@xaidenlabs/uso 1.1.61 β 1.1.63
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 +127 -3
- package/package.json +1 -1
- package/src/commands/doctor.js +40 -0
- package/src/commands/init.js +23 -10
- package/src/commands/uninstall.js +0 -2
- package/src/commands/workflow.js +8 -21
- package/src/platforms/wsl.js +39 -1
package/README.md
CHANGED
|
@@ -61,6 +61,27 @@ The installer will:
|
|
|
61
61
|
|
|
62
62
|
---
|
|
63
63
|
|
|
64
|
+
### Stealth WSL Mode (Windows Only)
|
|
65
|
+
|
|
66
|
+
On Windows, USO can install the entire toolchain inside a hidden WSL2 Linux distribution called the **Uso Engine**. This avoids Windows-specific issues like Smart App Control, symlink errors, and "Access Denied" problems entirely.
|
|
67
|
+
|
|
68
|
+
**Enable Stealth Mode:**
|
|
69
|
+
```bash
|
|
70
|
+
uso init --wsl
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
Once enabled, all subsequent commands (`uso build`, `uso test`, `uso val`, etc.) are automatically routed through the WSL engine. You stay in PowerShellβthe Linux layer is completely invisible.
|
|
74
|
+
|
|
75
|
+
**How it works:**
|
|
76
|
+
- USO installs a minimal Ubuntu WSL2 distro and hides it from Windows Terminal.
|
|
77
|
+
- Rust, Solana CLI, and Anchor are installed inside the distro.
|
|
78
|
+
- Commands are transparently bridged: you run `uso build` in PowerShell, and it executes `anchor build` inside WSL.
|
|
79
|
+
- The local validator binds to `localhost`, so your tests connect seamlessly.
|
|
80
|
+
|
|
81
|
+
**Configuration** is stored in `~/.uso-config.json`. To switch back to native mode, delete this file or reinstall without `--wsl`.
|
|
82
|
+
|
|
83
|
+
---
|
|
84
|
+
|
|
64
85
|
### Granular Installation
|
|
65
86
|
|
|
66
87
|
Use the `install` command to set up individual components if you do not require the full stack.
|
|
@@ -82,8 +103,6 @@ uso install anchor
|
|
|
82
103
|
|
|
83
104
|
---
|
|
84
105
|
|
|
85
|
-
---
|
|
86
|
-
|
|
87
106
|
### Project Scaffolding
|
|
88
107
|
|
|
89
108
|
Start a new project with a robust, pre-configured Anchor template.
|
|
@@ -99,6 +118,88 @@ This generates a "batteries-included" workspace with:
|
|
|
99
118
|
|
|
100
119
|
---
|
|
101
120
|
|
|
121
|
+
### Workflow Commands
|
|
122
|
+
|
|
123
|
+
USO wraps the core Anchor and Solana CLI commands so you don't need to worry about PATH issues or WSL routing.
|
|
124
|
+
|
|
125
|
+
**Build your program:**
|
|
126
|
+
```bash
|
|
127
|
+
uso build
|
|
128
|
+
```
|
|
129
|
+
|
|
130
|
+
**Run tests:**
|
|
131
|
+
```bash
|
|
132
|
+
uso test
|
|
133
|
+
```
|
|
134
|
+
On Windows, USO automatically checks if a validator is running before starting tests, preventing hangs.
|
|
135
|
+
|
|
136
|
+
**Deploy your program:**
|
|
137
|
+
```bash
|
|
138
|
+
uso deploy
|
|
139
|
+
```
|
|
140
|
+
|
|
141
|
+
**Clean build artifacts:**
|
|
142
|
+
```bash
|
|
143
|
+
uso clean
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
---
|
|
147
|
+
|
|
148
|
+
### Wallet & SOL Commands
|
|
149
|
+
|
|
150
|
+
Manage your Solana wallet and devnet SOL directly from USO.
|
|
151
|
+
|
|
152
|
+
**Show your wallet address:**
|
|
153
|
+
```bash
|
|
154
|
+
uso address
|
|
155
|
+
```
|
|
156
|
+
|
|
157
|
+
**Check your SOL balance:**
|
|
158
|
+
```bash
|
|
159
|
+
uso balance
|
|
160
|
+
```
|
|
161
|
+
|
|
162
|
+
**Check balance of a specific address:**
|
|
163
|
+
```bash
|
|
164
|
+
uso balance <address>
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
**Airdrop SOL (devnet/testnet):**
|
|
168
|
+
```bash
|
|
169
|
+
uso airdrop 2
|
|
170
|
+
uso airdrop 5 <recipient-address>
|
|
171
|
+
```
|
|
172
|
+
|
|
173
|
+
---
|
|
174
|
+
|
|
175
|
+
### Developer Tools
|
|
176
|
+
|
|
177
|
+
**Start a local test validator:**
|
|
178
|
+
```bash
|
|
179
|
+
uso validator
|
|
180
|
+
# or the shorthand:
|
|
181
|
+
uso val
|
|
182
|
+
```
|
|
183
|
+
|
|
184
|
+
Pass flags directly to the validator:
|
|
185
|
+
```bash
|
|
186
|
+
uso val --reset
|
|
187
|
+
```
|
|
188
|
+
|
|
189
|
+
On Windows, if the validator encounters "Access Denied" errors, USO automatically retries in an elevated Administrator terminal with Windows Defender exclusions applied.
|
|
190
|
+
|
|
191
|
+
**Full developer mode (Validator + Watcher):**
|
|
192
|
+
```bash
|
|
193
|
+
uso dev
|
|
194
|
+
```
|
|
195
|
+
|
|
196
|
+
This command:
|
|
197
|
+
1. Starts (or detects) a local validator.
|
|
198
|
+
2. Runs your test suite.
|
|
199
|
+
3. Watches for `.rs` and `.ts` file changes and automatically re-runs tests.
|
|
200
|
+
|
|
201
|
+
---
|
|
202
|
+
|
|
102
203
|
### Verification
|
|
103
204
|
|
|
104
205
|
After installation, verify that all components are correctly configured and accessible in your system PATH.
|
|
@@ -127,7 +228,7 @@ If your builds fail with `os error 4551` or "Access Denied" due to Smart App Con
|
|
|
127
228
|
|
|
128
229
|
USO provides a clean uninstallation process to remove the installed toolchains.
|
|
129
230
|
|
|
130
|
-
**Remove All Components:**
|
|
231
|
+
**Remove All Components (interactive):**
|
|
131
232
|
```bash
|
|
132
233
|
uso uninstall
|
|
133
234
|
```
|
|
@@ -141,6 +242,29 @@ uso uninstall anchor
|
|
|
141
242
|
|
|
142
243
|
---
|
|
143
244
|
|
|
245
|
+
## Command Reference
|
|
246
|
+
|
|
247
|
+
| Command | Description |
|
|
248
|
+
|---|---|
|
|
249
|
+
| `uso init` | Install full stack (Rust, Solana, Anchor) |
|
|
250
|
+
| `uso init --wsl` | Install via Stealth WSL Engine (Windows) |
|
|
251
|
+
| `uso doctor` | Diagnose environment issues |
|
|
252
|
+
| `uso verify` | Verify toolchain with test build |
|
|
253
|
+
| `uso create <name>` | Scaffold a new Anchor project |
|
|
254
|
+
| `uso build` | Build the Anchor program |
|
|
255
|
+
| `uso test` | Run Anchor tests |
|
|
256
|
+
| `uso deploy` | Deploy the program |
|
|
257
|
+
| `uso clean` | Clean build artifacts |
|
|
258
|
+
| `uso address` | Show wallet address |
|
|
259
|
+
| `uso balance [addr]` | Show SOL balance |
|
|
260
|
+
| `uso airdrop <amt> [to]` | Airdrop SOL |
|
|
261
|
+
| `uso val` / `uso validator` | Start local test validator |
|
|
262
|
+
| `uso dev` | Dev mode (validator + watcher) |
|
|
263
|
+
| `uso unblock` | Unblock files on Windows |
|
|
264
|
+
| `uso uninstall [component]` | Remove installed toolchains |
|
|
265
|
+
|
|
266
|
+
---
|
|
267
|
+
|
|
144
268
|
## Troubleshooting
|
|
145
269
|
|
|
146
270
|
- **"Permission Denied" Errors**: If you encounter errors related to permissions or symlinks, try running your terminal as an Administrator.
|
package/package.json
CHANGED
package/src/commands/doctor.js
CHANGED
|
@@ -13,6 +13,44 @@ const checkGit = (silent = false) => {
|
|
|
13
13
|
return installed;
|
|
14
14
|
};
|
|
15
15
|
|
|
16
|
+
const checkWsl = (silent = false) => {
|
|
17
|
+
// Only relevant on Windows
|
|
18
|
+
if (os.platform() !== 'win32') return true;
|
|
19
|
+
|
|
20
|
+
// 1. Check wsl.exe exists
|
|
21
|
+
const hasWslBinary = !!shell.which('wsl');
|
|
22
|
+
if (!hasWslBinary) {
|
|
23
|
+
if (!silent) {
|
|
24
|
+
log.error("β WSL not installed");
|
|
25
|
+
log.warn(" π Run 'uso install' to automatically install WSL (admin permission required).");
|
|
26
|
+
}
|
|
27
|
+
return false;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
// 2. Check WSL feature is active
|
|
31
|
+
const statusCheck = shell.exec('wsl --status', { silent: true });
|
|
32
|
+
if (statusCheck.code !== 0) {
|
|
33
|
+
if (!silent) {
|
|
34
|
+
log.warn("β οΈ WSL is installed but not fully configured (restart may be pending).");
|
|
35
|
+
log.warn(" π Try restarting your PC, then run 'uso install' again.");
|
|
36
|
+
}
|
|
37
|
+
return false;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
// 3. Check Ubuntu distro is ready
|
|
41
|
+
const ubuntuCheck = shell.exec('wsl -d Ubuntu -e true', { silent: true });
|
|
42
|
+
if (ubuntuCheck.code !== 0) {
|
|
43
|
+
if (!silent) {
|
|
44
|
+
log.warn("β οΈ WSL installed but Ubuntu distro is not yet set up.");
|
|
45
|
+
log.warn(" π Run 'uso install' to finish the setup.");
|
|
46
|
+
}
|
|
47
|
+
return false;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
if (!silent) log.success("β
WSL installed and Ubuntu ready");
|
|
51
|
+
return true;
|
|
52
|
+
};
|
|
53
|
+
|
|
16
54
|
const checkRust = (silent = false) => {
|
|
17
55
|
const rustc = shell.exec('rustc --version', { silent: true });
|
|
18
56
|
const installed = rustc.code === 0;
|
|
@@ -111,6 +149,7 @@ const doctor = async () => {
|
|
|
111
149
|
log.header(`π©Ί Running Doctor for ${platform}...`);
|
|
112
150
|
|
|
113
151
|
checkGit();
|
|
152
|
+
if (platform === 'win32') checkWsl();
|
|
114
153
|
checkRust();
|
|
115
154
|
checkSolana();
|
|
116
155
|
checkAnchor();
|
|
@@ -120,6 +159,7 @@ const doctor = async () => {
|
|
|
120
159
|
module.exports = {
|
|
121
160
|
doctor,
|
|
122
161
|
checkGit,
|
|
162
|
+
checkWsl,
|
|
123
163
|
checkRust,
|
|
124
164
|
checkSolana,
|
|
125
165
|
checkAnchor,
|
package/src/commands/init.js
CHANGED
|
@@ -10,23 +10,36 @@ const { ensureWalletInteractive } = require('../utils/wallet');
|
|
|
10
10
|
const path = require('path');
|
|
11
11
|
const fs = require('fs');
|
|
12
12
|
|
|
13
|
-
const { installWsl } = require('../platforms/wsl');
|
|
13
|
+
const { installWsl, installWslFeature } = require('../platforms/wsl');
|
|
14
14
|
|
|
15
15
|
const init = async (component, options) => {
|
|
16
16
|
const platform = os.platform();
|
|
17
17
|
|
|
18
|
-
// ---
|
|
18
|
+
// --- On Windows, ALWAYS use the WSL path ---
|
|
19
19
|
if (platform === 'win32') {
|
|
20
|
-
const
|
|
21
|
-
// Check if WSL + Ubuntu is available (quick check: wsl -d Ubuntu -e true)
|
|
22
|
-
const wslCheck = shell.exec('wsl -d Ubuntu -e true', { silent: true });
|
|
23
|
-
const wslAvailable = wslCheck.code === 0;
|
|
20
|
+
const hasWslBinary = !!shell.which('wsl');
|
|
24
21
|
|
|
25
|
-
if (
|
|
26
|
-
|
|
27
|
-
|
|
22
|
+
if (!hasWslBinary) {
|
|
23
|
+
// WSL is not installed at all β request admin elevation to enable the feature
|
|
24
|
+
log.header("π§ Windows Subsystem for Linux (WSL) not found.");
|
|
25
|
+
log.info("π‘οΈ Requesting administrator permission to install WSL...");
|
|
26
|
+
log.info("π Please click 'Yes' in the UAC popup that appears to allow this.");
|
|
27
|
+
console.log("");
|
|
28
|
+
|
|
29
|
+
const wslInstalled = await installWslFeature();
|
|
30
|
+
|
|
31
|
+
if (!wslInstalled) {
|
|
32
|
+
// installWslFeature already printed the relevant error/reboot message
|
|
33
|
+
return;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
// If we're here, WSL was instantly available (rare β usually needs reboot)
|
|
37
|
+
// Fall through to installWsl() below
|
|
28
38
|
}
|
|
29
|
-
|
|
39
|
+
|
|
40
|
+
// WSL binary is present β run the full WSL toolchain install
|
|
41
|
+
await installWsl();
|
|
42
|
+
return;
|
|
30
43
|
}
|
|
31
44
|
|
|
32
45
|
if (component) {
|
|
@@ -20,8 +20,6 @@ const askQuestion = (query) => {
|
|
|
20
20
|
* Runs a command and attempts to elevate privileges if it fails with a permission error.
|
|
21
21
|
*/
|
|
22
22
|
const runOrElevate = (command, description) => {
|
|
23
|
-
log.info(`Running: ${description}...`);
|
|
24
|
-
|
|
25
23
|
// We run without silent:true initially to let the user see output,
|
|
26
24
|
// but detecting the error code is what matters.
|
|
27
25
|
// actually, to detect the specific string "os error 1314", we need to capture output.
|
package/src/commands/workflow.js
CHANGED
|
@@ -15,19 +15,12 @@ const runProxyCommand = async (command, args = [], binary = 'anchor') => {
|
|
|
15
15
|
const nativeAvailable = shell.which(binary);
|
|
16
16
|
if (stealth.enabled && !nativeAvailable) {
|
|
17
17
|
const fullCommand = `${binary} ${command} ${args.join(' ')}`;
|
|
18
|
-
log.header(`π Running: ${fullCommand}`);
|
|
19
|
-
log.info(`π§ Routing through Uso Engine...`);
|
|
20
18
|
|
|
21
19
|
// Source cargo/solana paths inside WSL before running
|
|
22
20
|
const envSetup = 'source $HOME/.cargo/env 2>/dev/null; export PATH="$HOME/.local/share/solana/install/active_release/bin:$PATH"';
|
|
23
21
|
const wslCwd = toWslPath(process.cwd());
|
|
24
22
|
const execution = runWsl(`${envSetup} && ${fullCommand}`, { distro: stealth.distro, cwd: process.cwd() });
|
|
25
23
|
|
|
26
|
-
if (execution.code === 0) {
|
|
27
|
-
log.success(`β
'${command}' completed successfully.`);
|
|
28
|
-
} else {
|
|
29
|
-
log.error(`β '${command}' failed.`);
|
|
30
|
-
}
|
|
31
24
|
return;
|
|
32
25
|
}
|
|
33
26
|
|
|
@@ -40,12 +33,10 @@ const runProxyCommand = async (command, args = [], binary = 'anchor') => {
|
|
|
40
33
|
}
|
|
41
34
|
|
|
42
35
|
const fullCommand = `${binary} ${command} ${args.join(' ')}`;
|
|
43
|
-
log.header(`π Running: ${fullCommand}`);
|
|
44
36
|
|
|
45
37
|
const execution = shell.exec(fullCommand);
|
|
46
38
|
|
|
47
39
|
if (execution.code === 0) {
|
|
48
|
-
log.success(`β
'${command}' completed successfully.`);
|
|
49
40
|
return;
|
|
50
41
|
}
|
|
51
42
|
|
|
@@ -61,7 +52,7 @@ const runProxyCommand = async (command, args = [], binary = 'anchor') => {
|
|
|
61
52
|
} else {
|
|
62
53
|
log.warn("β οΈ Windows requires Administrator privileges for this operation.");
|
|
63
54
|
}
|
|
64
|
-
|
|
55
|
+
|
|
65
56
|
|
|
66
57
|
// Clean stale blocked artifacts before elevated retry (only for cargo/anchor builds)
|
|
67
58
|
if (isAppControlBlock && binary === 'anchor') {
|
|
@@ -72,7 +63,7 @@ const runProxyCommand = async (command, args = [], binary = 'anchor') => {
|
|
|
72
63
|
|
|
73
64
|
await runElevatedWithProgress(command, args, binary);
|
|
74
65
|
} else {
|
|
75
|
-
|
|
66
|
+
// Command failed (non-elevated)
|
|
76
67
|
}
|
|
77
68
|
};
|
|
78
69
|
|
|
@@ -91,8 +82,7 @@ const runElevatedWithProgress = (command, args = [], binary = 'anchor') => {
|
|
|
91
82
|
// 1. Prepare progress file
|
|
92
83
|
try { fs.writeFileSync(progressFile, ''); } catch (e) { }
|
|
93
84
|
|
|
94
|
-
|
|
95
|
-
log.warn("π Output will be mirrored below. Keep the new window open!");
|
|
85
|
+
|
|
96
86
|
|
|
97
87
|
// 2. Construct Elevated Command
|
|
98
88
|
const innerCmd = `
|
|
@@ -239,8 +229,6 @@ const validator = async (args = []) => {
|
|
|
239
229
|
const cmdArgs = flags.join(' ');
|
|
240
230
|
const fullCmd = `solana-test-validator ${cmdArgs}`;
|
|
241
231
|
|
|
242
|
-
log.header(`π Starting Validator via Uso Engine...`);
|
|
243
|
-
log.info(`π§ Running: ${fullCmd}`);
|
|
244
232
|
log.info("π Press Ctrl+C to stop it.");
|
|
245
233
|
|
|
246
234
|
const envSetup = 'source $HOME/.cargo/env 2>/dev/null; export PATH="$HOME/.local/share/solana/install/active_release/bin:$PATH"';
|
|
@@ -304,7 +292,6 @@ const validator = async (args = []) => {
|
|
|
304
292
|
const cmdArgs = flags.join(' ');
|
|
305
293
|
const fullCmd = cmdArgs ? `solana-test-validator ${cmdArgs}` : 'solana-test-validator';
|
|
306
294
|
|
|
307
|
-
log.header(`π Starting Solana Test Validator (${fullCmd})...`);
|
|
308
295
|
log.info("π Press Ctrl+C to stop it.");
|
|
309
296
|
|
|
310
297
|
// Run and capture exit code
|
|
@@ -324,7 +311,7 @@ const validator = async (args = []) => {
|
|
|
324
311
|
const flagStr = flags.join(' ');
|
|
325
312
|
const targetCmd = `solana-test-validator ${flagStr}`;
|
|
326
313
|
|
|
327
|
-
|
|
314
|
+
|
|
328
315
|
log.warn("π A new window will appear. Keep it open to run the validator!");
|
|
329
316
|
|
|
330
317
|
// Robust Launch using EncodedCommand to avoid quoting hell and set CWD correctly
|
|
@@ -385,7 +372,7 @@ const validator = async (args = []) => {
|
|
|
385
372
|
|
|
386
373
|
const unblock = () => {
|
|
387
374
|
const cwd = process.cwd();
|
|
388
|
-
|
|
375
|
+
|
|
389
376
|
|
|
390
377
|
if (os.platform() !== 'win32') {
|
|
391
378
|
log.success("β
Not on Windows, nothing to unblock.");
|
|
@@ -424,7 +411,7 @@ module.exports = {
|
|
|
424
411
|
|
|
425
412
|
const dev = async () => {
|
|
426
413
|
const stealth = isStealthMode();
|
|
427
|
-
|
|
414
|
+
|
|
428
415
|
|
|
429
416
|
// 1. Check if validator is running
|
|
430
417
|
const isValidatorRunning = () => {
|
|
@@ -440,7 +427,7 @@ const dev = async () => {
|
|
|
440
427
|
if (isValidatorRunning()) {
|
|
441
428
|
log.success("β
Validator is already running.");
|
|
442
429
|
} else {
|
|
443
|
-
|
|
430
|
+
|
|
444
431
|
// Spawn validator (this will open the Admin window)
|
|
445
432
|
// We use [] args to start cleanly but persistently.
|
|
446
433
|
// If it fails, the user will see it in the new window.
|
|
@@ -463,7 +450,7 @@ const dev = async () => {
|
|
|
463
450
|
}
|
|
464
451
|
}
|
|
465
452
|
|
|
466
|
-
|
|
453
|
+
|
|
467
454
|
// Fix: Pass --skip-local-validator directly (without --) so Anchor consumes it
|
|
468
455
|
test(['--skip-local-validator']);
|
|
469
456
|
|
package/src/platforms/wsl.js
CHANGED
|
@@ -7,6 +7,44 @@ const os = require('os');
|
|
|
7
7
|
const { spawnSync } = require('child_process');
|
|
8
8
|
const chalk = require('chalk');
|
|
9
9
|
|
|
10
|
+
/**
|
|
11
|
+
* Installs the WSL Windows Feature via an elevated PowerShell UAC prompt.
|
|
12
|
+
* This is needed when `wsl.exe` is not present on the system at all.
|
|
13
|
+
* Returns true if WSL is now available after the attempt, false otherwise.
|
|
14
|
+
*/
|
|
15
|
+
const installWslFeature = async () => {
|
|
16
|
+
log.warn("β οΈ WSL (Windows Subsystem for Linux) is not installed on this machine.");
|
|
17
|
+
log.info("π‘οΈ Administrator permission is required to install WSL.");
|
|
18
|
+
log.info("π A UAC (User Account Control) popup will appear β please click 'Yes' to allow the installation.");
|
|
19
|
+
console.log("");
|
|
20
|
+
|
|
21
|
+
// Run `wsl --install --no-distribution` elevated.
|
|
22
|
+
// --no-distribution: only enables the WSL feature, does not pull a distro yet.
|
|
23
|
+
// We wait for it to finish (-Wait) so we can check the result.
|
|
24
|
+
const elevateCmd = `powershell -Command "Start-Process -FilePath 'wsl.exe' -ArgumentList '--install', '--no-distribution' -Verb RunAs -Wait"`;
|
|
25
|
+
const result = shell.exec(elevateCmd, { silent: false });
|
|
26
|
+
|
|
27
|
+
if (result.code !== 0) {
|
|
28
|
+
// User likely denied UAC or the command failed
|
|
29
|
+
log.error("β WSL installation was cancelled or failed.");
|
|
30
|
+
log.warn("π To install manually, open PowerShell as Administrator and run:");
|
|
31
|
+
console.log(chalk.bold.yellow(" wsl --install"));
|
|
32
|
+
return false;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
// Verify wsl is now available
|
|
36
|
+
const check = shell.exec('wsl --status', { silent: true });
|
|
37
|
+
if (check.code !== 0) {
|
|
38
|
+
// WSL was just installed β a reboot is almost certainly required
|
|
39
|
+
log.warn("β οΈ WSL feature has been installed, but a system restart is required to complete setup.");
|
|
40
|
+
log.warn("π Please RESTART your computer, then run `uso install` again to set up the toolchain.");
|
|
41
|
+
return false; // Signal caller that we need a restart before proceeding
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
log.success("β
WSL feature installed successfully.");
|
|
45
|
+
return true;
|
|
46
|
+
};
|
|
47
|
+
|
|
10
48
|
const installWsl = async () => {
|
|
11
49
|
log.header("π§ Configuring Stealth WSL Environment...");
|
|
12
50
|
|
|
@@ -272,4 +310,4 @@ const hideFromWindowsTerminal = () => {
|
|
|
272
310
|
}
|
|
273
311
|
};
|
|
274
312
|
|
|
275
|
-
module.exports = { installWsl };
|
|
313
|
+
module.exports = { installWslFeature, installWsl };
|