feat: initial commit — antigravity proxy with MITM, standalone LS, and snapshot tooling

This commit is contained in:
Nikketryhard
2026-02-14 02:24:35 -06:00
commit d5e7f09225
30 changed files with 9980 additions and 0 deletions

217
src/constants.rs Normal file
View File

@@ -0,0 +1,217 @@
//! Shared constants — auto-detected from the installed Antigravity binary at startup.
//!
//! On first access, we locate the Antigravity installation (via the running
//! language server PID or well-known paths), parse `product.json` for version
//! strings, and extract Chrome/Electron versions from the binary. If detection
//! fails, we fall back to hardcoded values.
use std::fs;
use std::process::Command;
use std::sync::LazyLock;
/// Auto-detected version info from the installed Antigravity app.
struct DetectedVersions {
antigravity: String,
chrome: String,
electron: String,
client: String,
}
/// Locate the Antigravity install directory by tracing the language server PID
/// back to its binary, then walking up to the app root. Falls back to
/// well-known install paths.
fn find_install_dir() -> Option<String> {
// 1. Try tracing the running language server → /usr/share/antigravity/resources/app/extensions/...
if let Ok(output) = Command::new("sh")
.args(["-c", "pgrep -f language_server_linux | head -1"])
.output()
{
let pid = String::from_utf8_lossy(&output.stdout).trim().to_string();
if !pid.is_empty() {
if let Ok(exe) = fs::read_link(format!("/proc/{pid}/exe")) {
let exe_str = exe.to_string_lossy().to_string();
// exe is like: /usr/share/antigravity/resources/app/extensions/antigravity/bin/language_server_linux_x64
// We want: /usr/share/antigravity
if let Some(idx) = exe_str.find("/resources/") {
return Some(exe_str[..idx].to_string());
}
}
}
}
// 2. Fall back to well-known install paths
for path in &["/usr/share/antigravity", "/opt/Antigravity"] {
if fs::metadata(format!("{path}/resources/app/product.json")).is_ok() {
return Some(path.to_string());
}
}
None
}
/// Read `product.json` from the install dir and extract version fields.
fn read_product_json(install_dir: &str) -> (Option<String>, Option<String>) {
let path = format!("{install_dir}/resources/app/product.json");
let Ok(contents) = fs::read_to_string(&path) else {
return (None, None);
};
let Ok(json) = serde_json::from_str::<serde_json::Value>(&contents) else {
return (None, None);
};
let version = json["version"].as_str().map(|s| s.to_string());
let ide_version = json["ideVersion"].as_str().map(|s| s.to_string());
(version, ide_version)
}
/// Extract Chrome and Electron versions from the main binary via `strings`.
/// Pattern: "Chrome/142.0.7444.175", "Electron/39.2.3".
fn extract_binary_versions(install_dir: &str) -> (Option<String>, Option<String>) {
let binary = format!("{install_dir}/antigravity");
if fs::metadata(&binary).is_err() {
return (None, None);
}
// Use grep -oP on the binary to avoid loading the whole thing into memory
let chrome = Command::new("sh")
.args([
"-c",
&format!(
"strings '{}' | grep -oP 'Chrome/[0-9]+\\.[0-9]+\\.[0-9]+\\.[0-9]+' | head -1",
binary
),
])
.output()
.ok()
.and_then(|o| {
let s = String::from_utf8_lossy(&o.stdout).trim().to_string();
s.strip_prefix("Chrome/").map(|v| v.to_string())
});
let electron = Command::new("sh")
.args([
"-c",
&format!(
"strings '{}' | grep -oP 'Electron/[0-9]+\\.[0-9]+\\.[0-9]+' | head -1",
binary
),
])
.output()
.ok()
.and_then(|o| {
let s = String::from_utf8_lossy(&o.stdout).trim().to_string();
s.strip_prefix("Electron/").map(|v| v.to_string())
});
(chrome, electron)
}
/// Detect all versions from the installed Antigravity app.
fn detect_versions() -> DetectedVersions {
// Hardcoded fallbacks — last known good values
const FALLBACK_ANTIGRAVITY: &str = "1.107.0";
const FALLBACK_CHROME: &str = "142.0.7444.175";
const FALLBACK_ELECTRON: &str = "39.2.3";
const FALLBACK_CLIENT: &str = "1.16.5";
let Some(install_dir) = find_install_dir() else {
eprintln!(
"[constants] ⚠ Could not find Antigravity install — using fallback versions"
);
return DetectedVersions {
antigravity: FALLBACK_ANTIGRAVITY.to_string(),
chrome: FALLBACK_CHROME.to_string(),
electron: FALLBACK_ELECTRON.to_string(),
client: FALLBACK_CLIENT.to_string(),
};
};
// product.json → antigravity version + client/IDE version
let (ag_ver, client_ver) = read_product_json(&install_dir);
// Binary → Chrome + Electron versions
let (chrome_ver, electron_ver) = extract_binary_versions(&install_dir);
let versions = DetectedVersions {
antigravity: ag_ver.unwrap_or_else(|| FALLBACK_ANTIGRAVITY.to_string()),
chrome: chrome_ver.unwrap_or_else(|| FALLBACK_CHROME.to_string()),
electron: electron_ver.unwrap_or_else(|| FALLBACK_ELECTRON.to_string()),
client: client_ver.unwrap_or_else(|| FALLBACK_CLIENT.to_string()),
};
eprintln!(
"[constants] ✓ Detected versions: Antigravity={}, Chrome={}, Electron={}, Client={}",
versions.antigravity, versions.chrome, versions.electron, versions.client
);
versions
}
// ─── Public API ──────────────────────────────────────────────────────────────
/// All detected versions — computed once on first access.
static VERSIONS: LazyLock<DetectedVersions> = LazyLock::new(detect_versions);
/// Antigravity app version (e.g. "1.107.0").
pub fn antigravity_version() -> &'static str {
&VERSIONS.antigravity
}
/// Chrome version bundled with Electron (e.g. "142.0.7444.175").
pub fn chrome_version() -> &'static str {
&VERSIONS.chrome
}
/// Electron version (e.g. "39.2.3").
pub fn electron_version() -> &'static str {
&VERSIONS.electron
}
/// Client/IDE version from product.json (e.g. "1.16.5").
pub fn client_version() -> &'static str {
&VERSIONS.client
}
pub const CLIENT_NAME: &str = "antigravity";
pub const LS_SERVICE: &str = "exa.language_server_pb.LanguageServerService";
/// Log base directory for Antigravity.
pub fn log_base() -> String {
let home = std::env::var("HOME").unwrap_or_else(|_| "/root".to_string());
format!("{home}/.config/Antigravity/logs")
}
/// Token file path.
pub fn token_file_path() -> String {
let home = std::env::var("HOME").unwrap_or_else(|_| "/root".to_string());
format!("{home}/.config/antigravity-proxy-token")
}
/// User-Agent string matching the Electron webview — computed once.
pub static USER_AGENT: LazyLock<String> = LazyLock::new(|| {
format!(
"Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 \
(KHTML, like Gecko) Antigravity/{} \
Chrome/{} Electron/{} Safari/537.36",
antigravity_version(),
chrome_version(),
electron_version()
)
});
/// Chrome major version for sec-ch-ua header — computed once.
pub static CHROME_MAJOR: LazyLock<String> = LazyLock::new(|| {
chrome_version()
.split('.')
.next()
.unwrap_or("142")
.to_string()
});
/// Safely truncate a string to at most `max` characters (not bytes).
pub fn safe_truncate(s: &str, max: usize) -> String {
match s.char_indices().nth(max) {
None => s.to_string(),
Some((idx, _)) => format!("{}...", &s[..idx]),
}
}