@aiyiran/myclaw 1.1.136 → 1.1.137

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -808,8 +808,14 @@
808
808
  'background: #252536',
809
809
  ].join(';');
810
810
 
811
- // fetch → blob URL,绕过 CSP img-src 限制
811
+ // 远程环境:走 CDN(边缘缓存,速度快,不受本机出口带宽限制)
812
+ // 本地环境:走本地 API(文件尚未同步到 CDN)
813
+ // CSP img-src 限制后续在服务端统一放行,此处不做 blob 绕行
812
814
  var img = document.createElement('img');
815
+ var _imgEnv = detectEnvironment();
816
+ img.src = _imgEnv.remote
817
+ ? previewUrl + '?t=' + Date.now()
818
+ : MYCLAW_API_BASE + '/api/file?path=' + encodeURIComponent(getWorkspaceId() + '/' + asset.path) + '&t=' + Date.now();
813
819
  img.alt = asset.name || asset.path;
814
820
  img.style.cssText = [
815
821
  'max-width: 100%',
@@ -820,28 +826,13 @@
820
826
  'position: relative',
821
827
  'z-index: 1',
822
828
  ].join(';');
823
-
824
- function showImgError() {
829
+ img.onerror = function () {
825
830
  img.style.display = 'none';
826
831
  var errMsg = document.createElement('div');
827
832
  errMsg.textContent = '加载失败';
828
833
  errMsg.style.cssText = 'color:#666;font-size:13px;font-family:monospace;';
829
834
  imgArea.appendChild(errMsg);
830
- }
831
-
832
- var localImgUrl = MYCLAW_API_BASE + '/api/file?path=' + encodeURIComponent(getWorkspaceId() + '/' + asset.path) + '&t=' + Date.now();
833
- fetch(localImgUrl)
834
- .then(function (r) {
835
- if (!r.ok) throw new Error('HTTP ' + r.status);
836
- return r.blob();
837
- })
838
- .then(function (blob) {
839
- var blobUrl = URL.createObjectURL(blob);
840
- img.onload = function () { URL.revokeObjectURL(blobUrl); };
841
- img.onerror = showImgError;
842
- img.src = blobUrl;
843
- })
844
- .catch(showImgError);
835
+ };
845
836
 
846
837
  imgArea.appendChild(img);
847
838
  imgBox.appendChild(imgArea);
@@ -1179,11 +1170,17 @@
1179
1170
  var isVideo = VIDEO_EXTS.indexOf(assetExt) !== -1;
1180
1171
 
1181
1172
  if (isVideo) {
1182
- // 视频用 <video> 元素 + 本地 API,支持流式加载和拖拽进度条
1173
+ // <video> 元素支持 range 请求,流式加载,可拖拽进度条,不用 iframe
1174
+ // 远程环境:走 CDN(带宽快,不受本机出口限制)
1175
+ // 本地环境:走本地 API(文件尚未同步到 CDN)
1176
+ // CSP media-src 限制后续在服务端统一放行
1183
1177
  var video = document.createElement('video');
1184
1178
  video.controls = true;
1185
1179
  video.style.cssText = 'flex:1;width:100%;max-height:100%;background:#000;outline:none;';
1186
- video.src = MYCLAW_API_BASE + '/api/file?path=' + encodeURIComponent(getWorkspaceId() + '/' + asset.path);
1180
+ var _videoEnv = detectEnvironment();
1181
+ video.src = _videoEnv.remote
1182
+ ? previewUrl + '?t=' + Date.now()
1183
+ : MYCLAW_API_BASE + '/api/file?path=' + encodeURIComponent(getWorkspaceId() + '/' + asset.path);
1187
1184
  box.appendChild(video);
1188
1185
  overlay.appendChild(box);
1189
1186
  document.body.appendChild(overlay);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@aiyiran/myclaw",
3
- "version": "1.1.136",
3
+ "version": "1.1.137",
4
4
  "description": "",
5
5
  "main": "index.js",
6
6
  "bin": {
package/patches/patch.js CHANGED
@@ -113,6 +113,19 @@ function getMyclawVersion() {
113
113
  }
114
114
  }
115
115
 
116
+ /**
117
+ * 获取已安装的 OpenClaw 版本号
118
+ * uiDir 形如 <pkg>/dist/control-ui,包根目录为 uiDir/../..
119
+ */
120
+ function getOpenclawVersion(uiDir) {
121
+ try {
122
+ const pkgRoot = path.resolve(uiDir, '..', '..');
123
+ return require(path.join(pkgRoot, 'package.json')).version;
124
+ } catch {
125
+ return 'unknown';
126
+ }
127
+ }
128
+
116
129
  /**
117
130
  * 执行注入
118
131
  */
@@ -250,6 +263,13 @@ function patch() {
250
263
  let patched = false;
251
264
  let foundTarget = false;
252
265
 
266
+ // img-src / media-src 放宽仅针对特定 OpenClaw 版本(2026.6.9)。
267
+ // 该版本 CSP 中 img-src/media-src 为 'self' data: blob:,会拦截 CDN 图片/视频;
268
+ // 限定版本可避免误改其它版本(CSP 结构可能不同,盲目放宽有风险)。
269
+ const ocVersion = getOpenclawVersion(uiDir);
270
+ const needsMediaCspFix = ocVersion === '2026.6.9';
271
+ console.log('[myclaw-patch] → OpenClaw 版本: ' + ocVersion + (needsMediaCspFix ? ' (将额外放宽 img-src/media-src)' : ''));
272
+
253
273
  for (const f of distFiles) {
254
274
  // 兼容多版本:gateway-cli-*.js(旧)、server-*.js(中)、control-ui-*.js(新)
255
275
  const isTarget = (f.startsWith('gateway-cli-') || f.startsWith('server-') || f.startsWith('control-ui-')) && f.endsWith('.js');
@@ -264,7 +284,9 @@ function patch() {
264
284
  const needsFrameSrc = !content.includes('"frame-src *');
265
285
  const needsConnectSrc = !content.includes("connect-src *");
266
286
  const needsFrameAncestors = !content.includes("frame-ancestors *");
267
- const needsAnyCspPatch = needsFrameSrc || needsConnectSrc || needsFrameAncestors;
287
+ const needsImgSrc = needsMediaCspFix && !content.includes('"img-src *');
288
+ const needsMediaSrc = needsMediaCspFix && !content.includes('"media-src *');
289
+ const needsAnyCspPatch = needsFrameSrc || needsConnectSrc || needsFrameAncestors || needsImgSrc || needsMediaSrc;
268
290
 
269
291
  if (needsMicrophonePatch || needsAnyCspPatch) {
270
292
  // 备份
@@ -306,6 +328,16 @@ function patch() {
306
328
  content = content.replace(/\"frame-ancestors[^"]*\"/g, '"frame-ancestors *"');
307
329
  cspPatches.push('frame-ancestors *');
308
330
  }
331
+ // img-src → 允许所有(仅 2026.6.9,放行 CDN 图片)
332
+ if (needsImgSrc) {
333
+ content = content.replace(/\"img-src[^"]*\"/g, '"img-src *"');
334
+ cspPatches.push('img-src *');
335
+ }
336
+ // media-src → 允许所有(仅 2026.6.9,放行 CDN 视频)
337
+ if (needsMediaSrc) {
338
+ content = content.replace(/\"media-src[^"]*\"/g, '"media-src *"');
339
+ cspPatches.push('media-src *');
340
+ }
309
341
  if (cspPatches.length > 0) {
310
342
  console.log('[myclaw-patch] ✅ 已修复 CSP (' + cspPatches.join(', ') + '): ' + f);
311
343
  }