@synsci/cli 1.0.0 → 1.1.46
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/bin/synsc.js +93 -0
- package/package.json +7 -35
- package/postinstall.js +89 -0
- package/README.md +0 -39
- package/bin/cli.js +0 -8
- package/src/agents.js +0 -81
- package/src/ascii.js +0 -126
- package/src/index.js +0 -358
- package/src/installer.js +0 -611
- package/src/prompts.js +0 -529
package/bin/synsc.js
ADDED
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
const { spawnSync } = require("child_process")
|
|
4
|
+
const fs = require("fs")
|
|
5
|
+
const path = require("path")
|
|
6
|
+
const os = require("os")
|
|
7
|
+
|
|
8
|
+
// Check SYNSCI_BIN_PATH env var
|
|
9
|
+
const envPath = process.env.SYNSCI_BIN_PATH
|
|
10
|
+
if (envPath && fs.existsSync(envPath)) {
|
|
11
|
+
run(envPath)
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
const binary = os.platform() === "win32" ? "synsc.exe" : "synsc"
|
|
15
|
+
|
|
16
|
+
// Check ~/.synsc/bin first
|
|
17
|
+
const homeBin = path.join(os.homedir(), ".synsc", "bin", binary)
|
|
18
|
+
if (fs.existsSync(homeBin)) {
|
|
19
|
+
run(homeBin)
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
// Check /opt/homebrew/bin (macOS)
|
|
23
|
+
const brewBin = "/opt/homebrew/bin/synsc"
|
|
24
|
+
if (os.platform() === "darwin" && fs.existsSync(brewBin)) {
|
|
25
|
+
run(brewBin)
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
// Check /usr/local/bin
|
|
29
|
+
const localBin = "/usr/local/bin/synsc"
|
|
30
|
+
if (fs.existsSync(localBin)) {
|
|
31
|
+
run(localBin)
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
// Check sibling platform package
|
|
35
|
+
const scriptDir = path.dirname(fs.realpathSync(__filename))
|
|
36
|
+
const platformMap = { darwin: "darwin", linux: "linux", win32: "windows" }
|
|
37
|
+
const archMap = { x64: "x64", arm64: "arm64" }
|
|
38
|
+
const platform = platformMap[os.platform()] || os.platform()
|
|
39
|
+
const arch = archMap[os.arch()] || os.arch()
|
|
40
|
+
|
|
41
|
+
// Check local bin directory (set up by postinstall)
|
|
42
|
+
const localBinary = path.join(scriptDir, binary)
|
|
43
|
+
if (fs.existsSync(localBinary)) {
|
|
44
|
+
run(localBinary)
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
// Search node_modules for platform package
|
|
48
|
+
const base = `synsc-${platform}-${arch}`
|
|
49
|
+
let current = scriptDir
|
|
50
|
+
while (true) {
|
|
51
|
+
const modules = path.join(current, "node_modules")
|
|
52
|
+
if (fs.existsSync(modules)) {
|
|
53
|
+
const entries = fs.readdirSync(modules)
|
|
54
|
+
for (const entry of entries) {
|
|
55
|
+
if (entry.startsWith(base)) {
|
|
56
|
+
const candidate = path.join(modules, entry, "bin", binary)
|
|
57
|
+
if (fs.existsSync(candidate)) {
|
|
58
|
+
run(candidate)
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
// Also check scoped packages
|
|
63
|
+
const scoped = path.join(modules, "@synsci")
|
|
64
|
+
if (fs.existsSync(scoped)) {
|
|
65
|
+
const scopedEntries = fs.readdirSync(scoped)
|
|
66
|
+
for (const entry of scopedEntries) {
|
|
67
|
+
if (entry.startsWith("cli-" + platform + "-" + arch)) {
|
|
68
|
+
const candidate = path.join(scoped, entry, "bin", binary)
|
|
69
|
+
if (fs.existsSync(candidate)) {
|
|
70
|
+
run(candidate)
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
const parent = path.dirname(current)
|
|
77
|
+
if (parent === current) break
|
|
78
|
+
current = parent
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
console.error("synsc binary not found.")
|
|
82
|
+
console.error("Install with: curl -fsSL https://syntheticsciences.ai/install | bash")
|
|
83
|
+
console.error("Or set SYNSCI_BIN_PATH environment variable.")
|
|
84
|
+
process.exit(1)
|
|
85
|
+
|
|
86
|
+
function run(target) {
|
|
87
|
+
const result = spawnSync(target, process.argv.slice(2), { stdio: "inherit" })
|
|
88
|
+
if (result.error) {
|
|
89
|
+
console.error(result.error.message)
|
|
90
|
+
process.exit(1)
|
|
91
|
+
}
|
|
92
|
+
process.exit(typeof result.status === "number" ? result.status : 0)
|
|
93
|
+
}
|
package/package.json
CHANGED
|
@@ -1,44 +1,16 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@synsci/cli",
|
|
3
|
-
"version": "1.
|
|
4
|
-
"description": "Synthetic Sciences CLI - AI coding agent for machine learning
|
|
5
|
-
"
|
|
6
|
-
"access": "restricted"
|
|
7
|
-
},
|
|
8
|
-
"main": "src/index.js",
|
|
3
|
+
"version": "1.1.46",
|
|
4
|
+
"description": "Synthetic Sciences CLI - AI coding agent for machine learning research",
|
|
5
|
+
"license": "MIT",
|
|
9
6
|
"bin": {
|
|
10
|
-
"synsc": "./bin/
|
|
7
|
+
"synsc": "./bin/synsc.js"
|
|
11
8
|
},
|
|
12
|
-
"type": "module",
|
|
13
9
|
"scripts": {
|
|
14
|
-
"
|
|
15
|
-
"test": "node --test"
|
|
16
|
-
},
|
|
17
|
-
"keywords": [
|
|
18
|
-
"ai",
|
|
19
|
-
"ml",
|
|
20
|
-
"machine-learning",
|
|
21
|
-
"deep-learning",
|
|
22
|
-
"cli",
|
|
23
|
-
"coding-agent",
|
|
24
|
-
"synthetic-sciences"
|
|
25
|
-
],
|
|
26
|
-
"author": "Synthetic Sciences",
|
|
27
|
-
"license": "UNLICENSED",
|
|
28
|
-
"repository": {
|
|
29
|
-
"type": "git",
|
|
30
|
-
"url": "https://github.com/inkvell/synsc-cli.git"
|
|
31
|
-
},
|
|
32
|
-
"homepage": "https://syntheticsciences.com",
|
|
33
|
-
"bugs": {
|
|
34
|
-
"url": "https://github.com/inkvell/synsc-cli/issues"
|
|
10
|
+
"postinstall": "node postinstall.js"
|
|
35
11
|
},
|
|
12
|
+
"os": ["darwin", "linux", "win32"],
|
|
36
13
|
"engines": {
|
|
37
|
-
"node": ">=18
|
|
38
|
-
},
|
|
39
|
-
"dependencies": {
|
|
40
|
-
"chalk": "^5.3.0",
|
|
41
|
-
"inquirer": "^9.2.12",
|
|
42
|
-
"ora": "^8.0.1"
|
|
14
|
+
"node": ">=18"
|
|
43
15
|
}
|
|
44
16
|
}
|
package/postinstall.js
ADDED
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
|
|
3
|
+
const https = require("https")
|
|
4
|
+
const http = require("http")
|
|
5
|
+
const fs = require("fs")
|
|
6
|
+
const path = require("path")
|
|
7
|
+
const os = require("os")
|
|
8
|
+
const { execSync } = require("child_process")
|
|
9
|
+
|
|
10
|
+
const VERSION = "1.1.46"
|
|
11
|
+
|
|
12
|
+
const platformMap = { darwin: "darwin", linux: "linux", win32: "windows" }
|
|
13
|
+
const archMap = { x64: "x64", arm64: "arm64" }
|
|
14
|
+
|
|
15
|
+
const platform = platformMap[os.platform()]
|
|
16
|
+
const arch = archMap[os.arch()]
|
|
17
|
+
|
|
18
|
+
if (!platform || !arch) {
|
|
19
|
+
console.error(`Unsupported platform: ${os.platform()} ${os.arch()}`)
|
|
20
|
+
process.exit(1)
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
const binary = platform === "windows" ? "synsc.exe" : "synsc"
|
|
24
|
+
const ext = platform === "linux" ? ".tar.gz" : ".zip"
|
|
25
|
+
const filename = `synsc-${platform}-${arch}${ext}`
|
|
26
|
+
|
|
27
|
+
const binDir = path.join(__dirname, "bin")
|
|
28
|
+
const binPath = path.join(binDir, binary)
|
|
29
|
+
|
|
30
|
+
// Skip if binary already exists
|
|
31
|
+
if (fs.existsSync(binPath)) {
|
|
32
|
+
try {
|
|
33
|
+
const result = execSync(`"${binPath}" --version`, { encoding: "utf8", timeout: 5000 }).trim()
|
|
34
|
+
if (result) {
|
|
35
|
+
console.log(`synsc ${result} already installed`)
|
|
36
|
+
process.exit(0)
|
|
37
|
+
}
|
|
38
|
+
} catch {}
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
// Try to find existing installation
|
|
42
|
+
const homeBin = path.join(os.homedir(), ".synsc", "bin", binary)
|
|
43
|
+
if (fs.existsSync(homeBin)) {
|
|
44
|
+
console.log(`Found existing synsc at ${homeBin}`)
|
|
45
|
+
fs.mkdirSync(binDir, { recursive: true })
|
|
46
|
+
try {
|
|
47
|
+
fs.symlinkSync(homeBin, binPath)
|
|
48
|
+
console.log(`Linked to existing installation`)
|
|
49
|
+
process.exit(0)
|
|
50
|
+
} catch {
|
|
51
|
+
fs.copyFileSync(homeBin, binPath)
|
|
52
|
+
fs.chmodSync(binPath, 0o755)
|
|
53
|
+
console.log(`Copied from existing installation`)
|
|
54
|
+
process.exit(0)
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
// Check system PATH for synsc
|
|
59
|
+
try {
|
|
60
|
+
const systemBin = execSync("which synsc 2>/dev/null || where synsc 2>nul", { encoding: "utf8" }).trim()
|
|
61
|
+
if (systemBin && fs.existsSync(systemBin)) {
|
|
62
|
+
console.log(`Found synsc at ${systemBin}`)
|
|
63
|
+
fs.mkdirSync(binDir, { recursive: true })
|
|
64
|
+
try {
|
|
65
|
+
fs.symlinkSync(systemBin, binPath)
|
|
66
|
+
process.exit(0)
|
|
67
|
+
} catch {
|
|
68
|
+
fs.copyFileSync(systemBin, binPath)
|
|
69
|
+
fs.chmodSync(binPath, 0o755)
|
|
70
|
+
process.exit(0)
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
} catch {}
|
|
74
|
+
|
|
75
|
+
// Download from GitHub releases (private repo - needs token)
|
|
76
|
+
// or from the install script
|
|
77
|
+
console.log(`\nsynsc binary not found. Install it with:`)
|
|
78
|
+
console.log(` curl -fsSL https://syntheticsciences.ai/install | bash`)
|
|
79
|
+
console.log(`\nThen run: npm rebuild @synsci/cli`)
|
|
80
|
+
console.log(`Or set SYNSCI_BIN_PATH to point to your synsc binary.\n`)
|
|
81
|
+
|
|
82
|
+
// Create a placeholder script that shows the install message
|
|
83
|
+
fs.mkdirSync(binDir, { recursive: true })
|
|
84
|
+
fs.writeFileSync(binPath, `#!/usr/bin/env node
|
|
85
|
+
console.error("synsc binary not installed. Run: curl -fsSL https://syntheticsciences.ai/install | bash")
|
|
86
|
+
console.error("Then run: npm rebuild @synsci/cli")
|
|
87
|
+
process.exit(1)
|
|
88
|
+
`)
|
|
89
|
+
fs.chmodSync(binPath, 0o755)
|
package/README.md
DELETED
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
# @synsci/cli
|
|
2
|
-
|
|
3
|
-
Synthetic Sciences CLI - AI coding agent for machine learning engineers.
|
|
4
|
-
|
|
5
|
-
> **Note**: This is a private package. Access requires a Synthetic Sciences subscription.
|
|
6
|
-
|
|
7
|
-
## Installation
|
|
8
|
-
|
|
9
|
-
```bash
|
|
10
|
-
npm install -g @synsci/cli
|
|
11
|
-
```
|
|
12
|
-
|
|
13
|
-
## Usage
|
|
14
|
-
|
|
15
|
-
```bash
|
|
16
|
-
synsc
|
|
17
|
-
```
|
|
18
|
-
|
|
19
|
-
## Features
|
|
20
|
-
|
|
21
|
-
- **82 expert ML skills** built-in (GRPO, vLLM, DeepSpeed, Axolotl, etc.)
|
|
22
|
-
- **Native cloud integrations** (HuggingFace, W&B, Modal, Lambda Labs)
|
|
23
|
-
- **Tokens included** in your subscription
|
|
24
|
-
- **Model selection** (Claude 4.5, GPT-5.2, Gemini 3)
|
|
25
|
-
|
|
26
|
-
## Subscription
|
|
27
|
-
|
|
28
|
-
Visit [syntheticsciences.com](https://syntheticsciences.com) to subscribe.
|
|
29
|
-
|
|
30
|
-
| Plan | Price | Rate Limits |
|
|
31
|
-
|------|-------|-------------|
|
|
32
|
-
| Pro | $50/mo | ~1,000 requests/day |
|
|
33
|
-
| Pro+ | $200/mo | ~5,000 requests/day |
|
|
34
|
-
| Scale | $500/mo | ~20,000 requests/day |
|
|
35
|
-
| Enterprise | Custom | Unlimited |
|
|
36
|
-
|
|
37
|
-
## License
|
|
38
|
-
|
|
39
|
-
UNLICENSED - Synthetic Sciences
|
package/bin/cli.js
DELETED
package/src/agents.js
DELETED
|
@@ -1,81 +0,0 @@
|
|
|
1
|
-
import { existsSync } from 'fs';
|
|
2
|
-
import { homedir } from 'os';
|
|
3
|
-
import { join } from 'path';
|
|
4
|
-
|
|
5
|
-
/**
|
|
6
|
-
* Supported coding agents with their global config directories and skills paths
|
|
7
|
-
* All agents now support ~/.{agent}/skills/ format
|
|
8
|
-
*/
|
|
9
|
-
export const SUPPORTED_AGENTS = [
|
|
10
|
-
{
|
|
11
|
-
id: 'claude',
|
|
12
|
-
name: 'Claude Code',
|
|
13
|
-
configDir: '.claude',
|
|
14
|
-
skillsDir: 'skills',
|
|
15
|
-
},
|
|
16
|
-
{
|
|
17
|
-
id: 'cursor',
|
|
18
|
-
name: 'Cursor',
|
|
19
|
-
configDir: '.cursor',
|
|
20
|
-
skillsDir: 'skills',
|
|
21
|
-
},
|
|
22
|
-
{
|
|
23
|
-
id: 'codex',
|
|
24
|
-
name: 'Codex',
|
|
25
|
-
configDir: '.codex',
|
|
26
|
-
skillsDir: 'skills',
|
|
27
|
-
},
|
|
28
|
-
{
|
|
29
|
-
id: 'gemini',
|
|
30
|
-
name: 'Gemini CLI',
|
|
31
|
-
configDir: '.gemini',
|
|
32
|
-
skillsDir: 'skills',
|
|
33
|
-
},
|
|
34
|
-
{
|
|
35
|
-
id: 'qwen',
|
|
36
|
-
name: 'Qwen Code',
|
|
37
|
-
configDir: '.qwen',
|
|
38
|
-
skillsDir: 'skills',
|
|
39
|
-
},
|
|
40
|
-
];
|
|
41
|
-
|
|
42
|
-
/**
|
|
43
|
-
* Detect which coding agents are installed on the system
|
|
44
|
-
* @returns {Array} List of detected agents with their paths
|
|
45
|
-
*/
|
|
46
|
-
export function detectAgents() {
|
|
47
|
-
const home = homedir();
|
|
48
|
-
const detected = [];
|
|
49
|
-
|
|
50
|
-
for (const agent of SUPPORTED_AGENTS) {
|
|
51
|
-
const configPath = join(home, agent.configDir);
|
|
52
|
-
|
|
53
|
-
if (existsSync(configPath)) {
|
|
54
|
-
detected.push({
|
|
55
|
-
...agent,
|
|
56
|
-
path: `~/${agent.configDir}`,
|
|
57
|
-
fullPath: configPath,
|
|
58
|
-
skillsPath: join(configPath, agent.skillsDir),
|
|
59
|
-
});
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
return detected;
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
/**
|
|
67
|
-
* Get agent by ID
|
|
68
|
-
* @param {string} id Agent ID
|
|
69
|
-
* @returns {Object|null} Agent configuration or null
|
|
70
|
-
*/
|
|
71
|
-
export function getAgentById(id) {
|
|
72
|
-
return SUPPORTED_AGENTS.find(agent => agent.id === id) || null;
|
|
73
|
-
}
|
|
74
|
-
|
|
75
|
-
/**
|
|
76
|
-
* Get all supported agent IDs
|
|
77
|
-
* @returns {Array<string>} List of agent IDs
|
|
78
|
-
*/
|
|
79
|
-
export function getSupportedAgentIds() {
|
|
80
|
-
return SUPPORTED_AGENTS.map(agent => agent.id);
|
|
81
|
-
}
|
package/src/ascii.js
DELETED
|
@@ -1,126 +0,0 @@
|
|
|
1
|
-
import chalk from 'chalk';
|
|
2
|
-
|
|
3
|
-
// Clean capital ORCHESTRA
|
|
4
|
-
const logo = `
|
|
5
|
-
|
|
6
|
-
██████╗ ██████╗ ██████╗ ██╗ ██╗ ███████╗ ███████╗ ████████╗ ██████╗ █████╗
|
|
7
|
-
██╔═══██╗██╔══██╗██╔════╝ ██║ ██║ ██╔════╝ ██╔════╝ ╚══██╔══╝ ██╔══██╗ ██╔══██╗
|
|
8
|
-
██║ ██║██████╔╝██║ ███████║ █████╗ ███████╗ ██║ ██████╔╝ ███████║
|
|
9
|
-
██║ ██║██╔══██╗██║ ██╔══██║ ██╔══╝ ╚════██║ ██║ ██╔══██╗ ██╔══██║
|
|
10
|
-
╚██████╔╝██║ ██║╚██████╗ ██║ ██║ ███████╗ ███████║ ██║ ██║ ██║ ██║ ██║
|
|
11
|
-
╚═════╝ ╚═╝ ╚═╝ ╚═════╝ ╚═╝ ╚═╝ ╚══════╝ ╚══════╝ ╚═╝ ╚═╝ ╚═╝ ╚═╝ ╚═╝
|
|
12
|
-
|
|
13
|
-
`;
|
|
14
|
-
|
|
15
|
-
/**
|
|
16
|
-
* Welcome screen
|
|
17
|
-
*/
|
|
18
|
-
export function showWelcome(skillCount = 82, categoryCount = 20, agentCount = 5) {
|
|
19
|
-
console.clear();
|
|
20
|
-
console.log(chalk.white(logo));
|
|
21
|
-
console.log();
|
|
22
|
-
console.log(chalk.bold.white(' AI Research Skills'));
|
|
23
|
-
console.log();
|
|
24
|
-
console.log();
|
|
25
|
-
console.log(chalk.dim(' Expert-level knowledge for AI research engineering'));
|
|
26
|
-
console.log();
|
|
27
|
-
console.log();
|
|
28
|
-
console.log(` ${skillCount} skills · ${categoryCount} categories · ${agentCount} agents`);
|
|
29
|
-
console.log();
|
|
30
|
-
console.log();
|
|
31
|
-
}
|
|
32
|
-
|
|
33
|
-
/**
|
|
34
|
-
* Agents detected screen
|
|
35
|
-
*/
|
|
36
|
-
export function showAgentsDetected(agents) {
|
|
37
|
-
console.clear();
|
|
38
|
-
console.log(chalk.white(logo));
|
|
39
|
-
console.log();
|
|
40
|
-
console.log(chalk.bold.white(' AI Research Skills'));
|
|
41
|
-
console.log();
|
|
42
|
-
console.log();
|
|
43
|
-
console.log(chalk.green(` ✓ Found ${agents.length} coding agent${agents.length !== 1 ? 's' : ''}`));
|
|
44
|
-
console.log();
|
|
45
|
-
|
|
46
|
-
for (const agent of agents) {
|
|
47
|
-
console.log(` ${chalk.green('●')} ${chalk.white(agent.name.padEnd(14))} ${chalk.dim(agent.path)}`);
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
console.log();
|
|
51
|
-
console.log();
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
/**
|
|
55
|
-
* Menu header for inner screens
|
|
56
|
-
*/
|
|
57
|
-
export function showMenuHeader() {
|
|
58
|
-
console.clear();
|
|
59
|
-
console.log();
|
|
60
|
-
console.log(chalk.dim(' ────────────────────────────────────────────────────────────'));
|
|
61
|
-
console.log(chalk.white(' ORCHESTRA · AI Research Skills'));
|
|
62
|
-
console.log(chalk.dim(' ────────────────────────────────────────────────────────────'));
|
|
63
|
-
console.log();
|
|
64
|
-
}
|
|
65
|
-
|
|
66
|
-
/**
|
|
67
|
-
* Success screen
|
|
68
|
-
*/
|
|
69
|
-
export function showSuccess(skillCount, agents) {
|
|
70
|
-
console.clear();
|
|
71
|
-
console.log();
|
|
72
|
-
console.log();
|
|
73
|
-
console.log(chalk.green.bold(' ✓ Installation Complete'));
|
|
74
|
-
console.log();
|
|
75
|
-
console.log();
|
|
76
|
-
console.log(` Installed ${chalk.white(skillCount)} skills to ${chalk.white(agents.length)} agent${agents.length !== 1 ? 's' : ''}`);
|
|
77
|
-
console.log();
|
|
78
|
-
console.log(chalk.dim(' Your skills are now active and will appear when relevant.'));
|
|
79
|
-
console.log();
|
|
80
|
-
console.log();
|
|
81
|
-
console.log(chalk.dim(' ────────────────────────────────────────────────────────────'));
|
|
82
|
-
console.log();
|
|
83
|
-
console.log(chalk.white(' Examples:'));
|
|
84
|
-
console.log();
|
|
85
|
-
console.log(chalk.dim(' → "Help me set up GRPO training with verl"'));
|
|
86
|
-
console.log(chalk.dim(' → "How do I serve a model with vLLM?"'));
|
|
87
|
-
console.log(chalk.dim(' → "Write a NeurIPS paper introduction"'));
|
|
88
|
-
console.log();
|
|
89
|
-
console.log(chalk.dim(' ────────────────────────────────────────────────────────────'));
|
|
90
|
-
console.log();
|
|
91
|
-
console.log(chalk.white(' Commands:'));
|
|
92
|
-
console.log();
|
|
93
|
-
console.log(` ${chalk.dim('$')} ${chalk.cyan('npx @syntheticsciences/ai-research-skills')}`);
|
|
94
|
-
console.log(` ${chalk.dim('$')} ${chalk.cyan('npx @syntheticsciences/ai-research-skills list')}`);
|
|
95
|
-
console.log(` ${chalk.dim('$')} ${chalk.cyan('npx @syntheticsciences/ai-research-skills update')}`);
|
|
96
|
-
console.log();
|
|
97
|
-
console.log(chalk.dim(' ────────────────────────────────────────────────────────────'));
|
|
98
|
-
console.log();
|
|
99
|
-
console.log(chalk.dim(' github.com/syntheticsciences/ai-research-skills'));
|
|
100
|
-
console.log();
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
/**
|
|
104
|
-
* No agents found screen
|
|
105
|
-
*/
|
|
106
|
-
export function showNoAgents() {
|
|
107
|
-
console.clear();
|
|
108
|
-
console.log(chalk.white(logo));
|
|
109
|
-
console.log();
|
|
110
|
-
console.log(chalk.bold.white(' AI Research Skills'));
|
|
111
|
-
console.log();
|
|
112
|
-
console.log();
|
|
113
|
-
console.log(chalk.yellow(' ⚠ No coding agents detected'));
|
|
114
|
-
console.log();
|
|
115
|
-
console.log(chalk.dim(' Install one of these supported agents:'));
|
|
116
|
-
console.log();
|
|
117
|
-
console.log(' ○ Claude Code');
|
|
118
|
-
console.log(' ○ Cursor');
|
|
119
|
-
console.log(' ○ Codex (OpenAI)');
|
|
120
|
-
console.log(' ○ Windsurf');
|
|
121
|
-
console.log(' ○ Gemini CLI');
|
|
122
|
-
console.log(' ○ Kilo Code');
|
|
123
|
-
console.log(' ○ Qwen Code');
|
|
124
|
-
console.log();
|
|
125
|
-
console.log();
|
|
126
|
-
}
|