Skip to content

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

37 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Omnishell 🌐

The programmable, format-agnostic browser runtime powered by WebAssembly.

Stop rebuilding document viewers from scratch. Omnishell treats network protocols, compression algorithms, archive structures, and file formats as simple, hot-swappable Wasm plugins.

🚀 Out-of-the-Box Launch Capabilities

Omnishell includes a robust baseline layer, allowing developers to immediately build on top of standard web protocols:

  • Network Schemes: file:// (builtin) | http:// | https://
  • Compression: zstd | gzip | deflate | raw-deflate
  • Archives: zip
  • Transforms: markdownhtml
  • Views: html | svg | png | jpg | wasm (builtin)

🗺️ Roadmap

Planned features include cross format debugging and search capabilities by using the accessibility tree exported by view plugins and source maps exported by transform plugins, Omnishell delivers a built-in debug server and multimodal search natively across any file type.

🧪 The Innovation Sandbox

Omnishell was built to host next-generation computing formats. It serves as the official runtime and testing environment for:

  1. UMC (Universal Multimedia Codec): An ultra-efficient image/audio/video compression format reaching 0.1bpp @30+dB PSNR on video with symmetric 500MPs encoding/decoding throughput.
  2. LDP (Lean Document Package): A modern, document format engineered to replace PDF in the 21st century.

🛠️ Contribute Your Format

Want to bring Typst, Iroh, BitTorrent, Pdf, Brotli, or DjVu to Omnishell? Or integrate a js engine like Boa? Check out components/content/svg to see how to compile your first plugin to Wasm in minutes.

Technical overview

All plugins either take or return a Content type:

struct Content {
  url: String,
  info: MimeInfo,
  length: u64,
  content: ContentReader,
}

struct MimeInfo {
  /// corresponds to the http `content-type` header
  mime: String,
  /// corresponds to the http `content-encoding` header
  encoding: Option<String>,
}

There are several types of plugin:

  1. network plugin: handles a url scheme, takes an url and returns a content record. examples: http

  2. archive plugin: handles a mime type, takes a content record and a path and returns a new content record. examples: zip

  3. compression plugin: handles content-encoding, takes a content record with a content-encoding and returns a content record without a content-encoding. examples: zstd, deflate

  4. transform plugin: handles a mime type, takes a content record of one mime type and returns a content record of another mime type. optionally exposes a source map. examples: markdown, typst, latex

  5. view plugin: handles a mime type, takes a content record and returns an rgba frame. optionally handles input events, resources and child view plugins.

The role of the omnishell:

The omnishell handles the plugin lifecycle. To see how it works we will fetch the hypothetical url: https://omnishell.com/book.zip!/index.md.

  1. The url is parsed into the following parts:
  • scheme: https
  • base-url: https://omnishell.com/book.zip
  • path: index.md
  1. The file scheme is builtin to omnishell. If its the file scheme omnishell uses the extensions like .txt.gz to guess the mime text/plain and encoding gzip and creates a content record. Otherse the scheme handler is loaded from the plugin registry. In this case the http plugin is loaded.
  2. The http plugin is called with the base-url and a list of supported encodings. Since the deflate and zstd plugins are registered, the network plugin receives ['gzip', 'deflate', 'defalte-raw', 'zstd'].
  3. The http plugin performs a head request with the accept-encoding: identity, *;q=0 header to read the content-length, content-type and accept-ranges headers and the final redirected url.
  4. If the content-type starts with video/ or application/ streaming is enabled by default, so uncompressed range queries are made and retreived. For other content-types the entire file is fetched, providing the supported encodings with the accept-encoding header.
  5. In this case it is an application/zip content-type with no content-encoding and a path of index.md, so the archive plugin is loaded. The zip plugin supports content-types starting with application/zip or ending with +zip.
  6. The zip plugin guesses the content-type based on the file extension, in this case text/markdown and matches the zip compression method 8 to the content-encoding raw-deflate.
  7. The deflate compression plugin is loaded and applied.
  8. The text/markdown transform plugin is loaded and a text/html content record is returned.
  9. The text/html plugin is loaded and parses the html. It sees that the asset https://omnishell.com/book.zip!/image.png and the font https://omnishell.com/book.zip!/font.woff are missing. The font is fetched with fetch_bytes, doing the entire process again for font.woff. The bytes are then parsed and loaded in the webview. Image and svg assets are fetched with fetch_view, attaching a child view plugin to the html view plugin. The parent view can now forward input events and render the child view using the child widget id.
  10. The html view plugin is wrapped in a native widget and attached to the widget tree. It now handles input events forwarded by the widget wrapper and returns frames when requested.

License

MIT OR Apache-2.0

About

The programmable, format-agnostic browser runtime powered by WebAssembly.

Resources

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages