typescript-virtual-container 1.6.1 → 1.6.3
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.
- package/README.md +76 -43
- package/dist/.tsbuildinfo +1 -1
- package/dist/VirtualShell/index.d.ts +3 -0
- package/dist/VirtualShell/index.js +2 -0
- package/dist/commands/dpkg.js +1 -1
- package/dist/commands/expr.js +1 -1
- package/dist/commands/last.js +1 -1
- package/dist/commands/manuals-bundle.js +1 -1
- package/dist/commands/miscutils.js +3 -3
- package/dist/commands/mousepad.d.ts +2 -0
- package/dist/commands/mousepad.js +21 -0
- package/dist/commands/netcat.js +1 -1
- package/dist/commands/procUtils.js +1 -1
- package/dist/commands/registry.js +7 -0
- package/dist/commands/startxfce4.d.ts +2 -0
- package/dist/commands/startxfce4.js +13 -0
- package/dist/commands/sysinfo.js +3 -3
- package/dist/commands/textutils.js +2 -2
- package/dist/commands/top.js +1 -1
- package/dist/commands/uname.js +1 -1
- package/dist/commands/xfceDesktop.d.ts +2 -0
- package/dist/commands/xfceDesktop.js +13 -0
- package/dist/modules/VirtualNetworkManager.js +1 -0
- package/dist/modules/desktopManager.d.ts +104 -0
- package/dist/modules/desktopManager.js +896 -0
- package/dist/modules/linuxRootfs.js +125 -19
- package/dist/utils/keyToBytes.d.ts +1 -0
- package/dist/utils/keyToBytes.js +46 -0
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -13,7 +13,7 @@
|
|
|
13
13
|
## Table of Contents
|
|
14
14
|
|
|
15
15
|
- [Three ways to run](#three-ways-to-run) · [Get Started](#get-started)
|
|
16
|
-
- [How It Works](#how-it-works) · [Built-in Commands](#built-in-commands-
|
|
16
|
+
- [How It Works](#how-it-works) · [Built-in Commands](#built-in-commands-152)
|
|
17
17
|
- [Shell Scripting](#shell-scripting) · [Linux Rootfs](#linux-rootfs--vfs-path-resolution)
|
|
18
18
|
- [Configuration](#configuration) · [Troubleshooting](#troubleshooting)
|
|
19
19
|
- [FAQ](#faq) · [Contributing](#contributing)
|
|
@@ -27,8 +27,8 @@
|
|
|
27
27
|
| Mode | Entry point | Use case |
|
|
28
28
|
|------|-------------|----------|
|
|
29
29
|
| **SSH/SFTP server** | `VirtualSshServer` / `VirtualSftpServer` | Honeypots, remote testing, training environments |
|
|
30
|
-
| **Web shell** | `builds/fortune-nyx-v1.6.
|
|
31
|
-
| **Standalone CLI** | `builds/fortune-nyx-v1.6.
|
|
30
|
+
| **Web shell** | `builds/fortune-nyx-v1.6.3-web.min.js` (ESM) | Embedded terminals, interactive tutorials, browser demos — run `startxfce4` for a full XFCE desktop |
|
|
31
|
+
| **Standalone CLI** | `builds/fortune-nyx-v1.6.3-directbash-k6.1.0.mjs` (single file) | Local shell, one-liner demos, no install required |
|
|
32
32
|
<!-- /BUILD:mode-table -->
|
|
33
33
|
|
|
34
34
|
All three modes share the same core: a pure in-memory VFS, a real shell interpreter, a virtual package manager, and a typed programmatic API.
|
|
@@ -49,22 +49,22 @@ npm install typescript-virtual-container
|
|
|
49
49
|
<!-- BUILD:curl-start -->
|
|
50
50
|
#### Interactive local shell — persists VFS in .vfs/ in the current directory
|
|
51
51
|
```bash
|
|
52
|
-
curl -s https://raw.githubusercontent.com/itsrealfortune/typescript-virtual-container/refs/heads/main/builds/fortune-nyx-v1.6.
|
|
52
|
+
curl -s https://raw.githubusercontent.com/itsrealfortune/typescript-virtual-container/refs/heads/main/builds/fortune-nyx-v1.6.3-directbash-k6.1.0.mjs -o fortune-nyx-v1.6.3-directbash-k6.1.0.mjs && node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs
|
|
53
53
|
```
|
|
54
54
|
|
|
55
55
|
#### SSH server with built-in SFTP subsystem (scp / sftp on port 2222)
|
|
56
56
|
```bash
|
|
57
|
-
curl -s https://raw.githubusercontent.com/itsrealfortune/typescript-virtual-container/refs/heads/main/builds/fortune-nyx-v1.6.
|
|
57
|
+
curl -s https://raw.githubusercontent.com/itsrealfortune/typescript-virtual-container/refs/heads/main/builds/fortune-nyx-v1.6.3-ssh.cjs -o fortune-nyx-v1.6.3-ssh.cjs && node fortune-nyx-v1.6.3-ssh.cjs
|
|
58
58
|
```
|
|
59
59
|
|
|
60
60
|
#### Custom SSH port
|
|
61
61
|
```bash
|
|
62
|
-
node fortune-nyx-v1.6.
|
|
62
|
+
node fortune-nyx-v1.6.3-ssh.cjs --ssh-port=2022
|
|
63
63
|
```
|
|
64
64
|
|
|
65
65
|
#### SSH disabled (handler only, no server started)
|
|
66
66
|
```bash
|
|
67
|
-
node fortune-nyx-v1.6.
|
|
67
|
+
node fortune-nyx-v1.6.3-ssh.cjs --no-ssh
|
|
68
68
|
```
|
|
69
69
|
<!-- /BUILD:curl-start -->
|
|
70
70
|
|
|
@@ -72,16 +72,16 @@ node fortune-nyx-v1.6.1-ssh.cjs --no-ssh
|
|
|
72
72
|
> The standalone builds are intended for quick demos and testing. For production use, it's recommended to install the package and import the relevant classes directly in your codebase for better performance, stability, and security.
|
|
73
73
|
|
|
74
74
|
<!-- BUILD:selfStandalone-options -->
|
|
75
|
-
**`fortune-nyx-v1.6.
|
|
75
|
+
**`fortune-nyx-v1.6.3-directbash-k6.1.0.mjs` options:**
|
|
76
76
|
|
|
77
77
|
```bash
|
|
78
|
-
node fortune-nyx-v1.6.
|
|
79
|
-
node fortune-nyx-v1.6.
|
|
80
|
-
node fortune-nyx-v1.6.
|
|
81
|
-
node fortune-nyx-v1.6.
|
|
82
|
-
node fortune-nyx-v1.6.
|
|
83
|
-
node fortune-nyx-v1.6.
|
|
84
|
-
node fortune-nyx-v1.6.
|
|
78
|
+
node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs # boot as root
|
|
79
|
+
node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs --user alice # boot as alice (prompts for password if set)
|
|
80
|
+
node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs --user=alice # same, inline form
|
|
81
|
+
node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs --hostname=my-box # custom hostname
|
|
82
|
+
node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs --snapshot=/data/.vfs # custom VFS snapshot path
|
|
83
|
+
node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs --help # show all options
|
|
84
|
+
node fortune-nyx-v1.6.3-directbash-k6.1.0.mjs --version # print version
|
|
85
85
|
```
|
|
86
86
|
<!-- /BUILD:selfStandalone-options -->
|
|
87
87
|
|
|
@@ -108,7 +108,7 @@ Two browser bundles are available:
|
|
|
108
108
|
<!-- BUILD:web-table -->
|
|
109
109
|
| Bundle | Format | Entry point | Use case |
|
|
110
110
|
|--------|--------|-------------|----------|
|
|
111
|
-
| `builds/fortune-nyx-v1.6.
|
|
111
|
+
| `builds/fortune-nyx-v1.6.3-web.min.js` | ESM | `createWebShell()` | Embedded terminals, modern bundlers |
|
|
112
112
|
<!-- /BUILD:web-table -->
|
|
113
113
|
|
|
114
114
|
Both bundles persist the VFS in **IndexedDB** — state survives page reloads.
|
|
@@ -120,11 +120,11 @@ bun run build-all # rebuild everything
|
|
|
120
120
|
```
|
|
121
121
|
|
|
122
122
|
<!-- BUILD:web-options -->
|
|
123
|
-
**`fortune-nyx-v1.6.
|
|
123
|
+
**`fortune-nyx-v1.6.3-web.min.js`** — lightweight shell with IndexedDB VFS:
|
|
124
124
|
|
|
125
125
|
```html
|
|
126
126
|
<script type="module">
|
|
127
|
-
import { createWebShell } from "./builds/fortune-nyx-v1.6.
|
|
127
|
+
import { createWebShell } from "./builds/fortune-nyx-v1.6.3-web.min.js";
|
|
128
128
|
|
|
129
129
|
const shell = createWebShell("web-vm", {
|
|
130
130
|
vfs: { databaseName: "virtual-env-js", storeName: "vfs" },
|
|
@@ -136,11 +136,11 @@ bun run build-all # rebuild everything
|
|
|
136
136
|
</script>
|
|
137
137
|
```
|
|
138
138
|
|
|
139
|
-
**`fortune-nyx-v1.6.
|
|
139
|
+
**`fortune-nyx-v1.6.3-web.min.js`** — mirrors the `VirtualShell` programmatic API:
|
|
140
140
|
|
|
141
141
|
```html
|
|
142
142
|
<script type="module">
|
|
143
|
-
import { createVirtualShellShim } from "./builds/fortune-nyx-v1.6.
|
|
143
|
+
import { createVirtualShellShim } from "./builds/fortune-nyx-v1.6.3-web.min.js";
|
|
144
144
|
|
|
145
145
|
const shell = createVirtualShellShim("web-vm");
|
|
146
146
|
await shell.ensureInitialized();
|
|
@@ -186,13 +186,13 @@ console.log(r.stdout);
|
|
|
186
186
|
│ per-IP rate limiting / lockout home-dir confinement │
|
|
187
187
|
└─────────────────────────┬────────────────────────────────────────────────┘
|
|
188
188
|
│
|
|
189
|
-
┌──────────▼──────────┐
|
|
190
|
-
│ VirtualShell │
|
|
191
|
-
│ script parser │
|
|
192
|
-
│ command executor │
|
|
193
|
-
│ .bashrc loader │
|
|
194
|
-
│ session manager │
|
|
195
|
-
└──┬──────────────┬───┘
|
|
189
|
+
┌──────────▼──────────┐ ┌──────────────────────────┐
|
|
190
|
+
│ VirtualShell │────────▶ │ DesktopManager │
|
|
191
|
+
│ script parser │ │ XFCE panel · windows │
|
|
192
|
+
│ command executor │ │ Thunar · Mousepad │
|
|
193
|
+
│ .bashrc loader │ │ Trash · terminal windows│
|
|
194
|
+
│ session manager │ │ (browser only) │
|
|
195
|
+
└──┬──────────────┬───┘ └──────────────────────────┘
|
|
196
196
|
│ │
|
|
197
197
|
┌────────────▼───┐ ┌─────▼───────────────┐
|
|
198
198
|
│VirtualFileSystem│ │ VirtualUserManager │
|
|
@@ -211,7 +211,7 @@ console.log(r.stdout);
|
|
|
211
211
|
|
|
212
212
|
**What it is:** a shell emulator and virtual Linux environment for developer workflows.
|
|
213
213
|
|
|
214
|
-
**What it is not:** a
|
|
214
|
+
**What it is not:** a fully isolated sandbox. The shell commands are contained — no host binary is ever spawned, `execvp` is never called, `node`/`python3`/`npm` are virtual stubs. But `curl`/`wget` use the real `fetch()` API (live network access), all instances share the same JS heap as the host application, and CPU/memory are not capped. Do not expose to untrusted input without additional infrastructure-level isolation.
|
|
215
215
|
|
|
216
216
|
---
|
|
217
217
|
|
|
@@ -440,9 +440,9 @@ const [r1, r2] = await Promise.all([
|
|
|
440
440
|
---
|
|
441
441
|
|
|
442
442
|
<details>
|
|
443
|
-
<summary><strong>Built-in Commands (
|
|
443
|
+
<summary><strong>Built-in Commands (152)</strong></summary>
|
|
444
444
|
|
|
445
|
-
Type `help` in the shell for a grouped, colorized listing. Type `help <command>` for detailed usage. Type `man <command>` for full manual pages — all
|
|
445
|
+
Type `help` in the shell for a grouped, colorized listing. Type `help <command>` for detailed usage. Type `man <command>` for full manual pages — all commands are documented.
|
|
446
446
|
|
|
447
447
|
### Navigation
|
|
448
448
|
|
|
@@ -598,6 +598,16 @@ Type `help` in the shell for a grouped, colorized listing. Type `help <command>`
|
|
|
598
598
|
| `history [n]` | Command history |
|
|
599
599
|
| `help` | Full list: type `help` in the shell |
|
|
600
600
|
|
|
601
|
+
### Desktop (browser only)
|
|
602
|
+
|
|
603
|
+
| Command | Description |
|
|
604
|
+
|---------|-------------|
|
|
605
|
+
| `startxfce4` | Launch the XFCE desktop — blocks the shell until logout |
|
|
606
|
+
| `thunar [path]` | Open the file manager window |
|
|
607
|
+
| `mousepad [file]` | Open the text editor (`gedit` and `xed` are aliases) |
|
|
608
|
+
|
|
609
|
+
> Desktop commands are no-ops outside the browser environment.
|
|
610
|
+
|
|
601
611
|
### Fun
|
|
602
612
|
|
|
603
613
|
| Command | Description |
|
|
@@ -613,7 +623,7 @@ Type `help` in the shell for a grouped, colorized listing. Type `help <command>`
|
|
|
613
623
|
| `pacman` | Pacman game (mock) |
|
|
614
624
|
| `help` | Full list: type `help` in the shell |
|
|
615
625
|
|
|
616
|
-
**ℹ️ All
|
|
626
|
+
**ℹ️ All 152 built-in commands include complete JSDoc documentation** with `@category` and `@params` tags. See [src/commands/](https://github.com/itsrealfortune/typescript-virtual-container/tree/main/src/commands) for source code and inline documentation.
|
|
617
627
|
|
|
618
628
|
Custom commands: `shell.addCommand(name, params, callback)`.
|
|
619
629
|
|
|
@@ -954,27 +964,46 @@ import type {
|
|
|
954
964
|
|
|
955
965
|
## FAQ
|
|
956
966
|
|
|
957
|
-
**
|
|
958
|
-
|
|
967
|
+
**What exactly is this project?**
|
|
968
|
+
A self-contained Linux environment implemented entirely in TypeScript. It is not a mock, a stub, or a thin SSH wrapper — it is a full virtual container with its own filesystem (`VirtualFileSystem`), user and permission system (`VirtualUserManager`), shell interpreter, package manager, network layer, process table, and desktop environment. Each `VirtualShell` instance is an independent container that runs anywhere TypeScript runs: Node.js, Bun, or the browser.
|
|
969
|
+
|
|
970
|
+
**How is this different from a Docker container or a real VM?**
|
|
971
|
+
Docker and VMs enforce kernel-level isolation and run real binaries. This project runs entirely in the JavaScript runtime — no subprocess is ever spawned, no host binary is called. The trade-off is intentional: you get zero-dependency portability (including the browser), a fully inspectable and programmable environment, and no host OS requirements. It is not a security boundary.
|
|
972
|
+
|
|
973
|
+
**Is the environment fully isolated?**
|
|
974
|
+
No — and this is important to understand before exposing it to untrusted input:
|
|
975
|
+
|
|
976
|
+
- **Network is real.** `curl` and `wget` use the host's `fetch()` — requests reach the actual internet.
|
|
977
|
+
- **The JS heap is shared.** All `VirtualShell` instances run in the same JavaScript runtime as your application. There is no memory boundary between them or between the shell and the host.
|
|
978
|
+
- **No resource enforcement.** CPU usage and memory consumption are not capped by the container itself — a runaway loop consumes real host resources.
|
|
979
|
+
- **Filesystem isolation holds** in `"memory"` mode (the VFS never touches the host FS) and is limited to one `.vfsb` file in `"fs"` mode.
|
|
980
|
+
|
|
981
|
+
In short: the shell commands are sandboxed, the runtime is not.
|
|
959
982
|
|
|
960
983
|
**Can I use this in production?**
|
|
961
|
-
Yes for
|
|
984
|
+
Yes, for the right use cases: automated test harnesses, interactive tutorials, training environments, honeypots, and browser-based shell experiences. Do not expose it to arbitrary untrusted input without additional isolation at the infrastructure level — it is not a security boundary.
|
|
962
985
|
|
|
963
986
|
**Does the VFS touch the host filesystem?**
|
|
964
|
-
In `"memory"` mode:
|
|
987
|
+
In `"memory"` mode: never. In `"fs"` mode: exactly one binary file (`vfs-snapshot.vfsb`) inside `snapshotPath`. In the browser: IndexedDB only.
|
|
965
988
|
|
|
966
|
-
**Can I run multiple isolated
|
|
967
|
-
Yes. Each `new VirtualShell(...)` is
|
|
989
|
+
**Can I run multiple isolated environments in parallel?**
|
|
990
|
+
Yes. Each `new VirtualShell(...)` is fully independent — separate VFS, user database, environment state, and session manager. They share no global state.
|
|
968
991
|
|
|
969
992
|
**Does the shell support `&&`, `||`, `;`, and `&`?**
|
|
970
|
-
Yes — plus pipes, redirections, `if`/`for`/`while`/`case`, function definitions, and background jobs (`cmd &`).
|
|
993
|
+
Yes — plus pipes, redirections, `if`/`for`/`while`/`until`/`case`, function definitions, arrays, brace expansion, glob expansion, heredocs, `set -e`/`set -x`, and background jobs (`cmd &`).
|
|
971
994
|
|
|
972
995
|
**Can I use this for honeypot deployments?**
|
|
973
|
-
Yes —
|
|
996
|
+
Yes — `HoneyPot.attach()` captures every command, file write, auth attempt, and session event with timestamps. Configure `maxAuthAttempts` to throttle scanners. Export the audit log on shutdown.
|
|
974
997
|
|
|
975
998
|
**Is SFTP fully supported?**
|
|
976
999
|
Core operations are implemented. Extended attributes and symlinks return `OP_UNSUPPORTED`.
|
|
977
1000
|
|
|
1001
|
+
**Does the desktop work outside the browser?**
|
|
1002
|
+
No — `startxfce4`, `thunar`, and `mousepad` require a DOM. In Node.js/Bun they return an error immediately. The `DesktopManager` is only instantiated in the web shell example (`examples/app.ts`).
|
|
1003
|
+
|
|
1004
|
+
**What does the desktop simulate?**
|
|
1005
|
+
A single-user XFCE session: a panel with Applications menu and clock, draggable windows, a file manager (Thunar) with navigation, right-click context menu, rename, and trash, a text editor (Mousepad) with Ctrl+S save, and terminal windows each backed by a real interactive shell session against the same VFS.
|
|
1006
|
+
|
|
978
1007
|
---
|
|
979
1008
|
|
|
980
1009
|
## Contributing
|
|
@@ -993,8 +1022,9 @@ Core operations are implemented. Extended attributes and symlinks return `OP_UNS
|
|
|
993
1022
|
- Passwords hashed with scrypt (N=32768, r=8, p=1) with random per-user salt.
|
|
994
1023
|
- Root account always exists and cannot be deleted.
|
|
995
1024
|
- Per-IP rate limiting prevents automated brute-force on the SSH server.
|
|
996
|
-
- This project does **not** provide kernel-level or process-level isolation.
|
|
997
|
-
-
|
|
1025
|
+
- This project does **not** provide kernel-level or process-level isolation. All `VirtualShell` instances share the same JS heap as the host application.
|
|
1026
|
+
- `curl` and `wget` issue real network requests via `fetch()` — they are not sandboxed.
|
|
1027
|
+
- Do **not** expose to untrusted input without additional infrastructure-level isolation.
|
|
998
1028
|
|
|
999
1029
|
Vulnerability reports: contact maintainers privately before public disclosure — see `SECURITY.md`.
|
|
1000
1030
|
|
|
@@ -1018,6 +1048,8 @@ MIT — see [LICENSE](./LICENSE).
|
|
|
1018
1048
|
Open:
|
|
1019
1049
|
|
|
1020
1050
|
- [ ] WebSocket-based remote shell client (experimental)
|
|
1051
|
+
- [ ] XFCE desktop: resize windows, multi-monitor layout
|
|
1052
|
+
- [ ] Thunar: drag-and-drop between folders
|
|
1021
1053
|
|
|
1022
1054
|
<details>
|
|
1023
1055
|
<summary>Completed</summary>
|
|
@@ -1033,9 +1065,10 @@ Open:
|
|
|
1033
1065
|
- [x] Snapshot diff tooling — `diffSnapshots`, `formatDiff`, `assertDiff`
|
|
1034
1066
|
- [x] `node`/`python3`/`npm`/`npx` — package-gated virtual REPL stubs
|
|
1035
1067
|
<!-- BUILD:changelog -->
|
|
1036
|
-
- [x] Web shell bundles (`fortune-nyx-v1.6.
|
|
1037
|
-
- [x] Self-standalone CLI (`fortune-nyx-v1.6.
|
|
1068
|
+
- [x] Web shell bundles (`fortune-nyx-v1.6.3-web.min.js`) — fully browser-native with IndexedDB VFS
|
|
1069
|
+
- [x] Self-standalone CLI (`fortune-nyx-v1.6.3-directbash-k6.1.0.mjs`) — single-file interactive shell, per-user history, tab completion
|
|
1038
1070
|
<!-- /BUILD:changelog -->
|
|
1071
|
+
- [x] XFCE desktop simulation — `startxfce4` launches a full in-browser desktop with draggable windows, XFCE panel (Applications menu, clock, tray), Thunar file manager (navigate, right-click, trash, rename), Mousepad text editor (Ctrl+S, dirty indicator), terminal windows with live shell sessions, Font Awesome icons
|
|
1039
1072
|
- [x] 127+ `man` pages — all built-in commands documented via `man <cmd>`
|
|
1040
1073
|
- [x] Background job support — trailing `&` fires commands async; `:(){ :|:& };:` fork-bomb safely blocked by `MAX_CALL_DEPTH` guard; shell function names now accept any non-whitespace identifier (POSIX-compliant)
|
|
1041
1074
|
- [x] Shared `tokenize.ts` — unified tokenizer for shell parser and runtime (eliminates duplication)
|