aether-ai-agent-cli 1.1.9__tar.gz → 1.2.0__tar.gz

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.
Files changed (32) hide show
  1. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/PKG-INFO +1 -1
  2. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_ai_agent_cli.egg-info/PKG-INFO +1 -1
  3. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_ai_agent_cli.egg-info/SOURCES.txt +1 -0
  4. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/cli.py +1 -0
  5. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/package.json +1 -1
  6. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/chat.js +5 -0
  7. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/config.js +5 -1
  8. aether_ai_agent_cli-1.2.0/aether_pip/node_project/src/updater.js +186 -0
  9. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/LICENSE +0 -0
  10. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/README.md +0 -0
  11. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_ai_agent_cli.egg-info/dependency_links.txt +0 -0
  12. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_ai_agent_cli.egg-info/entry_points.txt +0 -0
  13. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_ai_agent_cli.egg-info/top_level.txt +0 -0
  14. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/__init__.py +0 -0
  15. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/bin/aether.js +0 -0
  16. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/package-lock.json +0 -0
  17. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/agent.js +0 -0
  18. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ai/fallback.js +0 -0
  19. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ai/google.js +0 -0
  20. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ai/providers.js +0 -0
  21. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ai/router.js +0 -0
  22. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ai/universal.js +0 -0
  23. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ai/xai.js +0 -0
  24. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/cli.js +0 -0
  25. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/file-parser.js +0 -0
  26. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/git.js +0 -0
  27. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/modes.js +0 -0
  28. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ui/banner.js +0 -0
  29. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ui/spinner.js +0 -0
  30. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/aether_pip/node_project/src/ui/theme.js +0 -0
  31. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/setup.cfg +0 -0
  32. {aether_ai_agent_cli-1.1.9 → aether_ai_agent_cli-1.2.0}/setup.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: aether-ai-agent-cli
3
- Version: 1.1.9
3
+ Version: 1.2.0
4
4
  Summary: Aether Core AI v110 — Universal AI Gateway CLI (Python Wrapper)
5
5
  Home-page: https://github.com/Krylo-60/aether-ai-cli
6
6
  Author: Krishiv PB
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: aether-ai-agent-cli
3
- Version: 1.1.9
3
+ Version: 1.2.0
4
4
  Summary: Aether Core AI v110 — Universal AI Gateway CLI (Python Wrapper)
5
5
  Home-page: https://github.com/Krylo-60/aether-ai-cli
6
6
  Author: Krishiv PB
@@ -18,6 +18,7 @@ aether_pip/node_project/src/config.js
18
18
  aether_pip/node_project/src/file-parser.js
19
19
  aether_pip/node_project/src/git.js
20
20
  aether_pip/node_project/src/modes.js
21
+ aether_pip/node_project/src/updater.js
21
22
  aether_pip/node_project/src/ai/fallback.js
22
23
  aether_pip/node_project/src/ai/google.js
23
24
  aether_pip/node_project/src/ai/providers.js
@@ -35,6 +35,7 @@ def main():
35
35
 
36
36
  try:
37
37
  # Run node aether.js passing all command line arguments
38
+ os.environ["AETHER_PACKAGER"] = "pip"
38
39
  cmd = ["node", aether_js] + sys.argv[1:]
39
40
  result = subprocess.run(cmd, check=False)
40
41
  sys.exit(result.returncode)
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@krishivpb60/aether-ai-cli",
3
- "version": "1.1.9",
3
+ "version": "1.2.0",
4
4
  "description": "Aether Core AI — A cyberpunk command-line AI assistant with multi-mode reasoning, 12-node failover mesh, file context injection, and offline fallbacks.",
5
5
  "main": "src/cli.js",
6
6
  "bin": {
@@ -45,6 +45,8 @@ import { MODES, DEFAULT_MODE, getModeByName } from "./modes.js";
45
45
  import { parseFile, formatContext } from "./file-parser.js";
46
46
  import { runMainframeHack } from "./ai/fallback.js";
47
47
  import { AGENT_INSTRUCTIONS } from "./agent.js";
48
+ import { checkForUpdates } from "./updater.js";
49
+
48
50
 
49
51
  // Configure marked dynamically for terminal output
50
52
  const getMarked = () => new Marked(markedTerminal({
@@ -67,6 +69,9 @@ export async function startChat(options = {}) {
67
69
  // Load AI config
68
70
  const aiConfig = await getAIConfig();
69
71
 
72
+ // Run update check
73
+ await checkForUpdates();
74
+
70
75
  // Set theme from configuration
71
76
  const theme = aiConfig.THEME || "cyberpunk";
72
77
  setTheme(theme);
@@ -173,7 +173,11 @@ export async function configExists() {
173
173
  export function isValidConfigKey(key) {
174
174
  const upper = key.toUpperCase();
175
175
  // Accept any API key or model override
176
- if (upper.endsWith("_API_KEY") || upper.endsWith("_API_KEYS") || upper.endsWith("_MODEL") || upper === "THEME" || upper === "CUSTOM_COMMANDS" || upper === "AUTOPILOT") {
176
+ const allowedSpecialKeys = [
177
+ "THEME", "CUSTOM_COMMANDS", "AUTOPILOT",
178
+ "AUTO_UPDATE", "SHOW_HIGHLIGHTS", "LAST_UPDATE_CHECK", "LAST_NOTIFIED_VERSION"
179
+ ];
180
+ if (upper.endsWith("_API_KEY") || upper.endsWith("_API_KEYS") || upper.endsWith("_MODEL") || allowedSpecialKeys.includes(upper)) {
177
181
  return true;
178
182
  }
179
183
  // Accept known config keys
@@ -0,0 +1,186 @@
1
+ // ═══════════════════════════════════════════════════════════
2
+ // AETHER AI CLI — Automated Update & Highlights Engine
3
+ // Checks NPM registry, updates packages, and renders release details.
4
+ // ═══════════════════════════════════════════════════════════
5
+
6
+ import { readFileSync } from "node:fs";
7
+ import { fileURLToPath } from "node:url";
8
+ import { dirname, join } from "node:path";
9
+ import { exec } from "node:child_process";
10
+ import { promisify } from "node:util";
11
+ import { getConfigValue, setConfigValue } from "./config.js";
12
+ import { colors, label, separator } from "./ui/theme.js";
13
+ import { createSpinner } from "./ui/spinner.js";
14
+
15
+ const execAsync = promisify(exec);
16
+
17
+ const __filename = fileURLToPath(import.meta.url);
18
+ const __dirname = dirname(__filename);
19
+ const pkg = JSON.parse(readFileSync(join(__dirname, "../package.json"), "utf8"));
20
+
21
+ /**
22
+ * Returns true if version 'latest' is newer than version 'current'.
23
+ * Supports standard semver format x.y.z.
24
+ * @param {string} latest
25
+ * @param {string} current
26
+ * @returns {boolean}
27
+ */
28
+ export function isNewerVersion(latest, current) {
29
+ const l = latest.split(".").map((num) => parseInt(num, 10) || 0);
30
+ const c = current.split(".").map((num) => parseInt(num, 10) || 0);
31
+ for (let i = 0; i < 3; i++) {
32
+ if (l[i] > c[i]) return true;
33
+ if (l[i] < c[i]) return false;
34
+ }
35
+ return false;
36
+ }
37
+
38
+ /**
39
+ * Fetches and displays release highlights from the remote repository.
40
+ * @param {string} version
41
+ */
42
+ export async function showReleaseHighlights(version) {
43
+ try {
44
+ const controller = new AbortController();
45
+ const timeoutId = setTimeout(() => controller.abort(), 2000);
46
+
47
+ const res = await fetch("https://raw.githubusercontent.com/Krylo-60/aether-ai-cli/main/HIGHLIGHTS.md", {
48
+ signal: controller.signal,
49
+ });
50
+ clearTimeout(timeoutId);
51
+
52
+ if (!res.ok) return;
53
+ const text = await res.text();
54
+
55
+ console.log("\n" + separator("━"));
56
+ console.log(colors.accent.bold(` ★ AETHER AI CLI v${version} RELEASE HIGHLIGHTS ★`));
57
+ console.log(separator("─"));
58
+
59
+ const lines = text.split("\n");
60
+ let inReleaseHeader = false;
61
+ let printedAny = false;
62
+
63
+ for (const line of lines) {
64
+ const trimmed = line.trim();
65
+ if (trimmed.startsWith("#")) {
66
+ // Matches the version header like "# Aether CLI v1.1.9 Highlights" or similar
67
+ if (trimmed.toLowerCase().includes(`v${version}`)) {
68
+ inReleaseHeader = true;
69
+ } else {
70
+ inReleaseHeader = false;
71
+ }
72
+ continue;
73
+ }
74
+
75
+ if (inReleaseHeader && trimmed) {
76
+ if (trimmed.startsWith("-") || trimmed.startsWith("*")) {
77
+ console.log(colors.brand(" " + trimmed));
78
+ printedAny = true;
79
+ } else {
80
+ console.log(colors.text(" " + trimmed));
81
+ printedAny = true;
82
+ }
83
+ }
84
+ }
85
+
86
+ if (!printedAny) {
87
+ // Fallback if no specific version section was found in HIGHLIGHTS.md
88
+ for (const line of lines) {
89
+ const trimmed = line.trim();
90
+ if (trimmed.startsWith("#")) continue;
91
+ if (trimmed.startsWith("-") || trimmed.startsWith("*")) {
92
+ console.log(colors.brand(" " + trimmed));
93
+ } else if (trimmed) {
94
+ console.log(colors.text(" " + trimmed));
95
+ }
96
+ }
97
+ }
98
+
99
+ console.log(separator("━") + "\n");
100
+ } catch {
101
+ // Fail silently (offline or repo down)
102
+ }
103
+ }
104
+
105
+ /**
106
+ * Checks for updates and runs the automatic updater if configured.
107
+ */
108
+ export async function checkForUpdates() {
109
+ const autoUpdate = (await getConfigValue("AUTO_UPDATE")) !== "false";
110
+ const showHighlights = (await getConfigValue("SHOW_HIGHLIGHTS")) !== "false";
111
+ const lastCheck = parseInt(await getConfigValue("LAST_UPDATE_CHECK") || "0", 10);
112
+ const now = Date.now();
113
+ const currentVersion = pkg.version;
114
+
115
+ // Run update check at most once every 24 hours (86,400,000 ms)
116
+ const checkInterval = 24 * 60 * 60 * 1000;
117
+ if (now - lastCheck < checkInterval) {
118
+ // Show highlights if we just updated and haven't shown highlights for this version
119
+ const lastNotified = await getConfigValue("LAST_NOTIFIED_VERSION") || "";
120
+ if (showHighlights && lastNotified !== currentVersion) {
121
+ await showReleaseHighlights(currentVersion);
122
+ await setConfigValue("LAST_NOTIFIED_VERSION", currentVersion);
123
+ }
124
+ return;
125
+ }
126
+
127
+ // Update check timestamp immediately
128
+ await setConfigValue("LAST_UPDATE_CHECK", now.toString());
129
+
130
+ try {
131
+ const controller = new AbortController();
132
+ const timeoutId = setTimeout(() => controller.abort(), 2000);
133
+
134
+ const res = await fetch("https://registry.npmjs.org/@krishivpb60/aether-ai-cli/latest", {
135
+ signal: controller.signal,
136
+ });
137
+ clearTimeout(timeoutId);
138
+
139
+ if (!res.ok) return;
140
+ const data = await res.json();
141
+ const latestVersion = data.version;
142
+
143
+ if (isNewerVersion(latestVersion, currentVersion)) {
144
+ if (autoUpdate) {
145
+ console.log("\n" + label.system + " " + colors.brand(`⚡ New version detected! Auto-updating from v${currentVersion} to v${latestVersion}...`));
146
+
147
+ const isPip = process.env.AETHER_PACKAGER === "pip";
148
+ const updateCmd = isPip
149
+ ? "pip install --upgrade aether-ai-agent-cli"
150
+ : "npm install -g @krishivpb60/aether-ai-cli";
151
+
152
+ try {
153
+ const spinner = createSpinner("Installing update").start();
154
+ await execAsync(updateCmd);
155
+ spinner.succeed("Update complete!");
156
+
157
+ console.log(label.system + " " + colors.success(`✓ Successfully updated to v${latestVersion}.`));
158
+
159
+ if (showHighlights) {
160
+ await showReleaseHighlights(latestVersion);
161
+ }
162
+ await setConfigValue("LAST_NOTIFIED_VERSION", latestVersion);
163
+ } catch (err) {
164
+ console.log(label.system + " " + colors.warning(`⚠ Auto-update failed: ${err.message}`));
165
+ console.log(label.system + " " + colors.muted(`Please run manually: ${updateCmd}`));
166
+ }
167
+ } else {
168
+ console.log("\n" + label.system + " " + colors.warning(`⚡ A new version (v${latestVersion}) is available!`));
169
+ const isPip = process.env.AETHER_PACKAGER === "pip";
170
+ const updateCmd = isPip
171
+ ? "pip install -U aether-ai-agent-cli"
172
+ : "npm install -g @krishivpb60/aether-ai-cli";
173
+ console.log(label.system + " " + colors.muted(`To update, run: ${updateCmd}`));
174
+ }
175
+ } else {
176
+ // Already on latest version, check if we need to show highlights
177
+ const lastNotified = await getConfigValue("LAST_NOTIFIED_VERSION") || "";
178
+ if (showHighlights && lastNotified !== currentVersion) {
179
+ await showReleaseHighlights(currentVersion);
180
+ await setConfigValue("LAST_NOTIFIED_VERSION", currentVersion);
181
+ }
182
+ }
183
+ } catch {
184
+ // Fail silently (offline or registry down)
185
+ }
186
+ }