@capawesome/cli
Version:
The Capawesome Cloud Command Line Interface (CLI) to manage Live Updates and more.
143 lines (142 loc) • 6.65 kB
JavaScript
;
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const axios_1 = require("axios");
const citty_1 = require("citty");
const consola_1 = __importDefault(require("consola"));
const open_1 = __importDefault(require("open"));
const config_1 = __importDefault(require("../services/config"));
const session_code_1 = __importDefault(require("../services/session-code"));
const sessions_1 = __importDefault(require("../services/sessions"));
const users_1 = __importDefault(require("../services/users"));
const error_1 = require("../utils/error");
const prompt_1 = require("../utils/prompt");
const userConfig_1 = __importDefault(require("../utils/userConfig"));
exports.default = (0, citty_1.defineCommand)({
meta: {
name: 'login',
description: 'Sign in to the Capawesome Cloud Console.',
},
args: {
token: {
type: 'string',
description: 'Token to use for authentication.',
},
},
run: (ctx) => __awaiter(void 0, void 0, void 0, function* () {
var _a;
const consoleBaseUrl = yield config_1.default.getValueForKey('CONSOLE_BASE_URL');
let sessionIdOrToken = ctx.args.token;
if (sessionIdOrToken === undefined) {
// @ts-ignore wait till https://github.com/unjs/consola/pull/280 is merged
const authenticationMethod = yield (0, prompt_1.prompt)('How would you like to authenticate Capawesome CLI?', {
type: 'select',
options: [
{ label: 'Login with a web browser', value: 'browser' },
{ label: 'Paste an authentication token', value: 'token' },
],
});
if (authenticationMethod === 'browser') {
// Create a session code
const { id: deviceCode, code: userCode } = yield session_code_1.default.create();
consola_1.default.box(`Copy your one-time code: ${userCode.slice(0, 4)}-${userCode.slice(4)}`);
// Prompt the user to open the authorization URL in their browser
const shouldProceed = yield (0, prompt_1.prompt)(`Select Yes to continue in your browser or No to cancel the authentication.`, {
type: 'confirm',
initial: true,
});
if (!shouldProceed) {
consola_1.default.error('Authentication cancelled.');
process.exit(1);
}
// Open the authorization URL in the user's default browser
consola_1.default.start('Opening browser...');
const authorizationUrl = `${consoleBaseUrl}/login/device`;
try {
(0, open_1.default)(authorizationUrl);
}
catch (error) {
consola_1.default.warn(`Could not open browser automatically. Please open the following URL manually: ${authorizationUrl}`);
}
// Wait for the user to authenticate
consola_1.default.start('Waiting for authentication...');
const sessionId = yield createSession(deviceCode);
if (!sessionId) {
consola_1.default.error('Authentication timed out. Please try again.');
process.exit(1);
}
sessionIdOrToken = sessionId;
}
else {
sessionIdOrToken = yield (0, prompt_1.prompt)('Please provide your authentication token:', {
type: 'text',
});
if (!sessionIdOrToken) {
consola_1.default.error('Token must be provided.');
process.exit(1);
}
}
}
else if (sessionIdOrToken.length === 0) {
// No token provided
consola_1.default.error(`Please provide a valid token. You can create a token at ${consoleBaseUrl}/settings/tokens.`);
process.exit(1);
}
// Sign in with the provided token
consola_1.default.start('Signing in...');
userConfig_1.default.write({
token: sessionIdOrToken,
});
try {
yield users_1.default.me();
consola_1.default.success(`Successfully signed in.`);
}
catch (error) {
userConfig_1.default.write({});
let message = (0, error_1.getMessageFromUnknownError)(error);
if (error instanceof axios_1.AxiosError && ((_a = error.response) === null || _a === void 0 ? void 0 : _a.status) === 401) {
message = `Invalid token. Please provide a valid token. You can create a token at ${consoleBaseUrl}/settings/tokens.`;
}
consola_1.default.error(message);
process.exit(1);
}
}),
});
const createSession = (deviceCode) => __awaiter(void 0, void 0, void 0, function* () {
var _a;
const maxAttempts = 20;
const interval = 3 * 1000; // 3 seconds
let attempts = 0;
let sessionId = null;
while (attempts < maxAttempts && sessionId === null) {
try {
const response = yield sessions_1.default.create({
code: deviceCode,
provider: 'code',
});
sessionId = response.id;
}
catch (error) {
if (error instanceof axios_1.AxiosError && ((_a = error.response) === null || _a === void 0 ? void 0 : _a.status) === 400) {
// Session not ready yet, wait and try again
attempts++;
yield new Promise((resolve) => setTimeout(resolve, interval));
}
else {
throw error;
}
}
}
return sessionId;
});