mira-app-server
Version:
Mira Server - standalone server application using mira-app-core
160 lines • 5.01 kB
JavaScript
;
/**
* 多 profile 凭证存储
*
* 将登录凭证持久化到 ~/.mira/credentials.json,支持多个命名 profile,
* 通过 current 指针记录当前激活的 profile,便于在不同服务器/账号间切换。
*
* 文件结构:
* {
* "current": "default",
* "profiles": {
* "default": { "server": "...", "token": "...", "username": "...", "updatedAt": "..." }
* }
* }
*/
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.CREDENTIALS_PATH = exports.MIRA_DIR = exports.DEFAULT_PROFILE_NAME = void 0;
exports.loadCredentials = loadCredentials;
exports.saveCredentials = saveCredentials;
exports.getProfile = getProfile;
exports.saveProfile = saveProfile;
exports.setCurrent = setCurrent;
exports.removeProfile = removeProfile;
exports.listProfiles = listProfiles;
exports.getCurrentProfile = getCurrentProfile;
exports.clearCurrentToken = clearCurrentToken;
const fs_1 = __importDefault(require("fs"));
const os_1 = __importDefault(require("os"));
const path_1 = __importDefault(require("path"));
/** 默认 profile 名 */
exports.DEFAULT_PROFILE_NAME = 'default';
/** 凭证目录:~/.mira */
exports.MIRA_DIR = path_1.default.join(os_1.default.homedir(), '.mira');
/** 凭证文件路径:~/.mira/credentials.json */
exports.CREDENTIALS_PATH = path_1.default.join(exports.MIRA_DIR, 'credentials.json');
/**
* 读取凭证文件,容错处理:
* - 文件不存在 → 返回空结构
* - 文件损坏/格式异常 → 返回空结构,不抛错(避免 CLI 崩溃)
*/
function loadCredentials() {
try {
if (!fs_1.default.existsSync(exports.CREDENTIALS_PATH)) {
return { profiles: {} };
}
const raw = fs_1.default.readFileSync(exports.CREDENTIALS_PATH, 'utf-8');
const parsed = JSON.parse(raw);
if (parsed &&
typeof parsed === 'object' &&
typeof parsed.profiles === 'object') {
return {
current: parsed.current,
profiles: parsed.profiles,
};
}
return { profiles: {} };
}
catch {
return { profiles: {} };
}
}
/**
* 写入凭证文件。目录不存在时自动创建(权限 0o700)。
*/
function saveCredentials(data) {
if (!fs_1.default.existsSync(exports.MIRA_DIR)) {
fs_1.default.mkdirSync(exports.MIRA_DIR, { recursive: true, mode: 0o700 });
}
fs_1.default.writeFileSync(exports.CREDENTIALS_PATH, JSON.stringify(data, null, 2), {
encoding: 'utf-8',
mode: 0o600,
});
}
/**
* 获取指定名称的 profile
*/
function getProfile(name) {
return loadCredentials().profiles[name];
}
/**
* 保存(新增或覆盖)一个 profile,并记录更新时间。
* 如果尚无 current,则将其设为当前。
*/
function saveProfile(name, profile) {
const data = loadCredentials();
data.profiles[name] = { ...profile, updatedAt: new Date().toISOString() };
if (!data.current) {
data.current = name;
}
saveCredentials(data);
}
/**
* 设置当前激活的 profile
* @returns 是否设置成功(profile 不存在则返回 false)
*/
function setCurrent(name) {
const data = loadCredentials();
if (!data.profiles[name]) {
return false;
}
data.current = name;
saveCredentials(data);
return true;
}
/**
* 删除一个 profile。若删除的是当前 profile,则清空 current。
*/
function removeProfile(name) {
const data = loadCredentials();
if (!data.profiles[name]) {
return false;
}
delete data.profiles[name];
if (data.current === name) {
data.current = Object.keys(data.profiles)[0];
}
saveCredentials(data);
return true;
}
/**
* 列出所有 profile 名
*/
function listProfiles() {
return Object.keys(loadCredentials().profiles);
}
/**
* 获取当前激活的 profile
* @returns { name, profile } 或 null(无任何 profile 时)
*/
function getCurrentProfile() {
const data = loadCredentials();
const current = data.current;
if (current && data.profiles[current]) {
return { name: current, profile: data.profiles[current] };
}
// current 失效时回退到第一个
const firstEntry = Object.entries(data.profiles)[0];
if (firstEntry) {
return { name: firstEntry[0], profile: firstEntry[1] };
}
return null;
}
/**
* 清空当前 profile 的 token(登出)。
* @returns 是否成功(无当前 profile 则返回 false)
*/
function clearCurrentToken() {
const data = loadCredentials();
if (!data.current || !data.profiles[data.current]) {
return false;
}
data.profiles[data.current].token = '';
data.profiles[data.current].updatedAt = new Date().toISOString();
saveCredentials(data);
return true;
}
//# sourceMappingURL=credentials.js.map