@web-sandbox.js/web-sandbox

0.0.1-alpha7 • Public • Published

WebSandbox

WebSandbox 基于 Realm Stage 2 规范实现,前一段时间 Realm 进入了 Stage 3,它有了非常大的 API 变更,这使得 WebSandbox 需要重新进行适配。

WebSandbox 的目标是构建一个安全且轻量化的浏览器虚拟化容器,它采用使用 Web 标准技术来构建,它的使用场景:

  • 作为 Web 应用的插件的安全运行环境、提供开放式的插件系统
  • 让不同的技术栈、版本的组件能够在同一个页面中运行,避免陷入重构的泥潭

https://web-sandbox.js.org/

安全模型

  • JS 语言安全——Realm: 基于 TC39 最新草案实现
  • CSS 安全——Shadow DOM: Web 正式标准
  • HTML 安全——Sanitizer: 基于 W3C 草案实现
  • 内容安全策略——CSP: 基于 W3C 正式标准实现

资源虚拟化

DOM 树

WebSandbox 拥有完整的 DOM 树结构,这些使用 ShadowRoot 隔离。

<web-sandbox>         ——— window
  #shadow-root        ——— document
    <html>            ——— document.documentElement
      <head></head>   ——— document.head
      <body></body>   ——— document.body
    </html>
</web-sandbox>

内容安全策略

可以通过 CSP 配置来控制应用内部的脚本、样式、链接、表单、网络请求等行为。

<web-sandbox
    name="sandbox-evaluate"
    csp="
      default-src 'none';
      script-src 'self' 'unsafe-inline' 'unsafe-eval' cdn.jsdelivr.net;
      style-src * 'unsafe-inline' cdn.jsdelivr.net;
      navigate-to 'self' web-sandbox.js.org;
    ">
</web-sandbox>

本地存储

拥有专属的本地存储空间,主文档或者父 WebSandbox 可以对它进行管理。

<web-sandbox
  id="box"
  text="
    localStorage.setItem('test', 1)
  ">
</web-sandbox>

Web Components

拥有完整的 Web Components 虚拟化实现,WebSandbox 内部注册的自定义元素不会影响主文档。

Viewport

WebSandbox 中的 CSS 无法影响主文档,包括设置了 position: fixed 元素、:host 选择器。

Task

requestAnimationFrame()setTimeout()setInterval() 等异步任务将随着 WebSandbox 销毁而自动结束。

ChildWebSandbox

WebSandbox 的应用内部也可以使用 WebSandbox,并且将继承内容安全策略。

<web-sandbox
    id="box"
    text="
      const sandbox = document.createElement('web-sandbox');
      sandbox.src = './child.js';
      document.body.appendChild(sandbox);
    ">
</web-sandbox>

标签

<web-sandbox name="application-name" src="https://cdn.jsdelivr.net/npm/application-name@3/dist/web-sandbox-application.demo.js">
</web-sandbox>

属性

name

沙箱应用名称。该名称可以用作为沙箱内 window.name 的值(也将作为内部分配本地缓存资源的命名空间)。

src

远程沙箱脚本地址。

text

本地的脚本内容。

contentWindow

沙箱内的 window 对象。只有在 <web-sandbox> 插入到文档后才可以访问到。

contentDocument

沙箱内的 document 对象。只有在 <web-sandbox> 插入到文档后才可以访问到。

csp

内容安全策略。CSP 可以精细化的指定沙箱的运行权限,例如限制数据请求等、禁止运行远程脚本等。这是 CSP 规范的子集。

如果不设置 csp 属性,那么 <web-sandbox> 将会启用默认指令 default-src none

支持的指令:

  • default-src
  • connect-src
  • script-src
  • style-src
  • form-action
  • navigate-to

source 支持的关键字:

  • 'none'
  • 'self'

示范:

<web-sandbox
    name="sandbox-evaluate"
    title="WebSandbox View"
    csp="
        default-src 'none';
        script-src 'self' 'unsafe-inline' 'unsafe-eval' cdn.jsdelivr.net;
        style-src * 'unsafe-inline' cdn.jsdelivr.net;
        navigate-to 'self' web-sandbox.js.org;
    ">
</web-sandbox>

更多 CSP 介绍:https://developer.mozilla.org/en-US/docs/Web/HTTP/CSP

限制

  • 受 Realm 垫片实现影响,远程的脚本与样式必须允许同源访问
  • 受 Realm 垫片实现影响,脚本中在严格模式下运行
  • 受 Realm 垫片实现影响,影响,脚本中不能包含 HTML 注释语句 <!--->
  • 受 Realm 垫片实现影响,影响,脚本中不能使用 ES6 import 导入模块
  • 受 Realm 垫片实现影响,影响,脚本中不能直接使用 eval() 语句;允许间接使用,例如 (0, eval)(code)。这个限制会导致一些依赖 eval() 语句动态编译模板的框架无法运行,这些模板必须在构建阶段编译后才能运行,例如 Vue
  • 受内置安全策略影响,不能使用主文档定义好的自定义元素
  • 受内置安全策略影响,脚本通过 element.innerHTML 等类似的 API 插入内容的时候可能会被过滤掉有危险的标签与属性
  • 受内置安全策略影响,主文档无法通过 localStorage 给沙箱脚本共享数据,因为 localStorage 被隔离
  • 受内置安全策略影响,无法捕获脚本运行时的全局错误,只允许主文档捕获
  • 不支持 CSS 的 vw/vh 单位
  • 不支持 CSS 媒体查询
  • 不支持 CSS 的 import 语句导入样式

受安全策略与项目进展的影响,浏览器的 API 以白名单的方式提供,细节请查阅 Web API 兼容性报告

Package Sidebar

Install

npm i @web-sandbox.js/web-sandbox

Weekly Downloads

0

Version

0.0.1-alpha7

License

none

Unpacked Size

138 kB

Total Files

4

Last publish

Collaborators

  • aui