UNPKG

mastra

Version:
244 lines (242 loc) • 7.9 kB
import { MASTRA_PLATFORM_API_URL } from './chunk-L2SGSIJI.js'; import { execFileSync } from 'child_process'; import { randomBytes } from 'crypto'; import { readFileSync } from 'fs'; import { mkdir, writeFile, chmod, readFile, unlink } from 'fs/promises'; import { createServer } from 'http'; import { homedir, release } from 'os'; import { join } from 'path'; var CREDENTIALS_DIR = join(homedir(), ".mastra"); var CREDENTIALS_FILE = join(CREDENTIALS_DIR, "credentials.json"); async function saveCredentials(creds) { await mkdir(CREDENTIALS_DIR, { recursive: true, mode: 448 }); await writeFile(CREDENTIALS_FILE, JSON.stringify(creds, null, 2), { mode: 384 }); await chmod(CREDENTIALS_DIR, 448).catch(() => { }); await chmod(CREDENTIALS_FILE, 384).catch(() => { }); } async function loadCredentials() { try { const data = await readFile(CREDENTIALS_FILE, "utf-8"); return JSON.parse(data); } catch { return null; } } async function clearCredentials() { try { await unlink(CREDENTIALS_FILE); } catch { } } async function getCurrentOrgId() { const envOrgId = process.env.MASTRA_ORG_ID; if (envOrgId) return envOrgId; const creds = await loadCredentials(); if (!creds) return null; return creds.currentOrgId ?? creds.organizationId; } async function setCurrentOrgId(orgId) { const creds = await loadCredentials(); if (!creds) throw new Error("Not logged in"); creds.currentOrgId = orgId; await saveCredentials(creds); } function isWSL() { if (process.platform !== "linux") return false; try { return /microsoft|wsl/i.test(release()) || /microsoft|wsl/i.test(readFileSync("/proc/version", "utf-8")); } catch { return false; } } function openBrowser(url) { if (process.platform === "darwin") { execFileSync("open", [url]); } else if (process.platform === "win32") { execFileSync("cmd", ["/c", "start", "", url]); } else if (isWSL()) { execFileSync("powershell.exe", ["-NoProfile", "-Command", `Start-Process '${url.replace(/'/g, "''")}'`]); } else { execFileSync("xdg-open", [url]); } } async function verifyToken(token) { try { const res = await fetch(`${MASTRA_PLATFORM_API_URL}/v1/auth/verify`, { headers: { Authorization: `Bearer ${token}` } }); return res.ok; } catch { return false; } } async function tryRefreshToken(creds) { if (!creds.refreshToken) return null; try { const res = await fetch(`${MASTRA_PLATFORM_API_URL}/v1/auth/refresh-token`, { method: "POST", headers: { "Content-Type": "application/json" }, body: JSON.stringify({ refreshToken: creds.refreshToken }) }); if (!res.ok) return null; const data = await res.json(); creds.token = data.accessToken; creds.refreshToken = data.refreshToken; await saveCredentials(creds); return data.accessToken; } catch { return null; } } function callbackPage({ success }) { const title = success ? "Logged in!" : "Login failed"; const message = success ? "You can close this tab and return to the terminal." : "Missing parameters. Close this tab and try again."; return `<!doctype html> <html lang="en"> <head> <meta charset="UTF-8" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> <title>${title} \u2014 Mastra</title> <style> body { margin: 0; padding: 0; background-color: #0d0d0d; color: #ffffff; font-family: 'Inter', -apple-system, BlinkMacSystemFont, system-ui, sans-serif; min-height: 100vh; display: flex; align-items: center; justify-content: center; } .container { text-align: center; } .logo { margin-bottom: 1.5rem; } h1 { font-size: 1.75rem; font-weight: 600; margin: 0 0 0.75rem 0; } p { color: #9ca3af; font-size: 1rem; margin: 0; line-height: 1.6; } </style> </head> <body> <div class="container"> <h1>${title}</h1> <p>${message}</p> </div> </body> </html>`; } async function login() { console.info("\nLogging in to Mastra...\n"); const server = createServer(); const state = randomBytes(16).toString("hex"); const port = await new Promise((resolve) => { server.listen(0, "127.0.0.1", () => { const addr = server.address(); if (typeof addr === "object" && addr) { resolve(addr.port); } }); }); const loginUrl = `${MASTRA_PLATFORM_API_URL}/v1/auth/login?product=cli&cli_port=${port}&state=${state}`; console.info(` Opening browser... `); try { openBrowser(loginUrl); } catch { console.info(` Could not open browser automatically.`); console.info(` Open this URL manually: ${loginUrl} `); if (isWSL()) { console.info(` Note: If login times out, ensure localhost forwarding is enabled in your .wslconfig. `); } } const result = await new Promise((resolve, reject) => { const timeout = setTimeout(() => { server.close(() => { reject(new Error("Login timed out (60s)")); }); server.closeAllConnections(); }, 6e4); server.on("request", (req, res) => { const url = new URL(req.url, `http://localhost:${port}`); if (url.pathname === "/callback") { const callbackState = url.searchParams.get("state"); const token = url.searchParams.get("token"); const refreshToken = url.searchParams.get("refresh_token"); const userParam = url.searchParams.get("user"); const orgId = url.searchParams.get("org"); if (callbackState !== state || !token || !userParam || !orgId) { res.writeHead(400, { "Content-Type": "text/html" }); res.end(callbackPage({ success: false })); return; } const user = JSON.parse(decodeURIComponent(userParam)); res.writeHead(200, { "Content-Type": "text/html", Connection: "close" }); res.end(callbackPage({ success: true })); clearTimeout(timeout); server.close(() => { resolve({ token, refreshToken, user, organizationId: orgId }); }); server.closeAllConnections(); } }); }); const creds = { token: result.token, ...result.refreshToken ? { refreshToken: result.refreshToken } : {}, user: result.user, organizationId: result.organizationId }; await saveCredentials(creds); console.info(` Logged in as ${creds.user.email} `); return creds; } function isInteractive() { return Boolean(process.stdin.isTTY && process.stdout.isTTY) && !process.env.CI; } async function getToken() { const envToken = process.env.MASTRA_API_TOKEN; if (envToken) return envToken; const creds = await loadCredentials(); if (!creds) { if (!isInteractive()) { throw new Error("Not logged in. Run `mastra auth login` interactively or set MASTRA_API_TOKEN."); } const newCreds2 = await login(); return newCreds2.token; } if (await verifyToken(creds.token)) return creds.token; const refreshed = await tryRefreshToken(creds); if (refreshed) return refreshed; if (!isInteractive()) { throw new Error("Session expired. Run `mastra auth login` interactively or set MASTRA_API_TOKEN."); } const newCreds = await login(); return newCreds.token; } async function validateOrgAccess(token, orgId) { const { fetchOrgs } = await import('./api-C4LNCE5C.js'); const orgs = await fetchOrgs(token); const hasAccess = orgs.some((o) => o.id === orgId); if (!hasAccess) { throw new Error(`No access to organization ${orgId}. Run: mastra auth orgs`); } } export { clearCredentials, getCurrentOrgId, getToken, loadCredentials, login, saveCredentials, setCurrentOrgId, tryRefreshToken, validateOrgAccess, verifyToken }; //# sourceMappingURL=chunk-EXG3XKBK.js.map //# sourceMappingURL=chunk-EXG3XKBK.js.map