UNPKG

kawazu

Version:

kawazu CLI tool for real-time chat in your editor

138 lines (137 loc) 6.18 kB
"use strict"; var __importDefault = (this && this.__importDefault) || function (mod) { return (mod && mod.__esModule) ? mod : { "default": mod }; }; Object.defineProperty(exports, "__esModule", { value: true }); exports.createRoom = createRoom; const chalk_1 = __importDefault(require("chalk")); const ora_1 = __importDefault(require("ora")); const inquirer_1 = __importDefault(require("inquirer")); const node_fetch_1 = __importDefault(require("node-fetch")); const config_1 = require("../utils/config"); const join_1 = require("./join"); async function createRoom(roomName, options) { // 認証チェック console.log(chalk_1.default.blue('🔍 認証状態を確認中...')); let config = await (0, config_1.requireAuth)(); const spinner = (0, ora_1.default)('ルームを作成中...').start(); try { // ルームスラッグの生成(ルーム名から自動生成) const slug = generateSlug(roomName); // プライベートルームの場合はパスワードを取得 let password = options.password; if (options.private && !password) { spinner.stop(); const { inputPassword } = await inquirer_1.default.prompt([ { type: 'password', name: 'inputPassword', message: 'プライベートルーム用のパスワードを入力してください:', validate: (input) => input.length >= 4 || 'パスワードは4文字以上で入力してください' } ]); password = inputPassword; spinner.start('ルームを作成中...'); } // API リクエストデータ const roomData = { name: roomName, slug: slug, is_private: options.private || false, password: password }; // API リクエスト(認証トークン付き) const response = await (0, node_fetch_1.default)(`${config.server_url}/api/rooms`, { method: 'POST', headers: { 'Content-Type': 'application/json', 'Authorization': `Bearer ${config.auth_token}` }, body: JSON.stringify(roomData) }); const result = await response.json(); if (!response.ok || !result.success) { spinner.fail('ルーム作成に失敗しました'); if (result.error) { console.error(chalk_1.default.red(`❌ ${result.error}`)); if (result.details) { result.details.forEach(detail => { console.error(chalk_1.default.red(` ${detail.field}: ${detail.message}`)); }); } } return; } spinner.succeed(`ルーム "${roomName}" を作成しました!`); // 作成したルームの情報を表示 console.log(chalk_1.default.green(`\n📝 ルーム情報:`)); console.log(` 名前: ${result.data.name}`); console.log(` ID: ${result.data.slug}`); console.log(` プライベート: ${result.data.is_private ? 'はい' : 'いいえ'}`); // CLIコマンドの表示 const cliCommand = result.data.is_private ? `kawazu join ${result.data.slug} -p ${password}` : `kawazu join ${result.data.slug}`; console.log(chalk_1.default.blue(`\n💡 参加コマンド:`)); console.log(chalk_1.default.cyan(` ${cliCommand}`)); // 自動参加の確認 const { autoJoin } = await inquirer_1.default.prompt([ { type: 'confirm', name: 'autoJoin', message: '作成したルームにすぐに参加しますか?', default: true } ]); if (autoJoin) { console.log(chalk_1.default.yellow('\n🚀 ルームに参加しています...\n')); // ユーザー名の取得(認証済みユーザー名を優先) const username = config.user_username || await promptUsername(); // 作成したルームに参加 await (0, join_1.joinRoom)(result.data.slug, { username, password: password }); } else { console.log(chalk_1.default.green('\n✅ ルームが作成されました。上記のコマンドで参加できます。')); } } catch (error) { spinner.fail('ルーム作成でエラーが発生しました'); console.error(chalk_1.default.red(`❌ ${error.message}`)); if (error.code === 'ECONNREFUSED') { console.log(chalk_1.default.yellow('💡 APIサーバーが起動していない可能性があります')); console.log(chalk_1.default.gray(` サーバーURL: ${config.server_url}`)); } } } function generateSlug(name) { return name .toLowerCase() .trim() .replace(/[^a-z0-9\s-]/g, '') // 英数字、スペース、ハイフンのみ残す .replace(/\s+/g, '-') // スペースをハイフンに変換 .replace(/-+/g, '-') // 連続ハイフンを1つに .replace(/^-|-$/g, ''); // 先頭末尾のハイフンを削除 } async function promptUsername() { const { username } = await inquirer_1.default.prompt([ { type: 'input', name: 'username', message: 'チャット用のユーザー名を入力してください:', validate: (input) => { const trimmed = input.trim(); if (trimmed.length === 0) return 'ユーザー名を入力してください'; if (trimmed.length > 50) return 'ユーザー名は50文字以内で入力してください'; if (!/^[a-zA-Z0-9_-]+$/.test(trimmed)) return 'ユーザー名は英数字、ハイフン、アンダースコアのみ使用できます'; return true; } } ]); return username.trim(); }