UNPKG

@aura-ai/cli

Version:

A Go-to-Market CLI tool for analyzing product positioning and market strategy

135 lines (134 loc) 6.15 kB
import React, { useState } from 'react'; import { Box, Text, useApp, useInput } from 'ink'; import { TextInput, Alert } from '@inkjs/ui'; import InitCommand from './commands/init.js'; /** * 6.1 Interactive interface main component */ export default function App() { const [mode, setMode] = useState('input'); const [inputValue, setInputValue] = useState(''); const [commandHistory, setCommandHistory] = useState([]); const [historyIndex, setHistoryIndex] = useState(-1); const [error, setError] = useState(''); const { exit } = useApp(); // 6.3 Command definitions const commands = [ { name: '/init', description: 'Analyze a project repository and generate GTM insights', handler: () => setMode('init') }, { name: '/help', description: 'Show available commands', handler: () => setMode('help') }, { name: '/exit', description: 'Exit the application', handler: () => exit() } ]; // 6.3 Parse and execute command const handleCommand = (command) => { const trimmedCommand = command.trim().toLowerCase(); // Add to history if (trimmedCommand && !commandHistory.includes(trimmedCommand)) { setCommandHistory([...commandHistory, trimmedCommand]); } // Reset history navigation setHistoryIndex(-1); setInputValue(''); setError(''); // Find and execute command const matchedCommand = commands.find(cmd => cmd.name === trimmedCommand); if (matchedCommand) { matchedCommand.handler(); } else if (trimmedCommand) { setError(`Unknown command: ${trimmedCommand}. Type /help for available commands.`); } }; // 6.7 Handle command history navigation useInput((input, key) => { if (mode !== 'input') return; if (key.upArrow && commandHistory.length > 0) { const newIndex = historyIndex < commandHistory.length - 1 ? historyIndex + 1 : commandHistory.length - 1; setHistoryIndex(newIndex); const historyValue = commandHistory[commandHistory.length - 1 - newIndex]; if (historyValue) { setInputValue(historyValue); } } else if (key.downArrow && historyIndex > 0) { const newIndex = historyIndex - 1; setHistoryIndex(newIndex); const historyValue = commandHistory[commandHistory.length - 1 - newIndex]; if (historyValue) { setInputValue(historyValue); } } else if (key.downArrow && historyIndex === 0) { setHistoryIndex(-1); setInputValue(''); } }); // Handle return from help mode useInput((input, key) => { if (mode === 'help' && (key.return || key.escape)) { setMode('input'); } }); // 6.7 Generate autocomplete suggestions const getSuggestions = () => { if (!inputValue.startsWith('/')) return []; return commands .map(cmd => cmd.name) .filter(name => name.startsWith(inputValue.toLowerCase())) .slice(0, 3); }; // Render based on current mode switch (mode) { case 'init': // 6.4 Render init command return (React.createElement(Box, { flexDirection: "column" }, React.createElement(InitCommand, null), React.createElement(Box, { marginTop: 1 }, React.createElement(Text, { dimColor: true }, "Press Ctrl+C to return to interactive mode")))); case 'help': // 6.5 Display help return (React.createElement(Box, { flexDirection: "column" }, React.createElement(Text, { bold: true, color: "cyan" }, "\uD83D\uDE80 Aura CLI - Available Commands"), React.createElement(Box, { marginTop: 1, flexDirection: "column" }, commands.map((cmd) => (React.createElement(Box, { key: cmd.name, marginBottom: 1 }, React.createElement(Text, { color: "green" }, cmd.name.padEnd(10)), React.createElement(Text, { dimColor: true }, cmd.description))))), React.createElement(Box, { marginTop: 1 }, React.createElement(Text, { dimColor: true }, "Press Enter or Escape to return...")))); case 'input': default: { // 6.2 Main input interface const suggestions = getSuggestions(); return (React.createElement(Box, { flexDirection: "column" }, React.createElement(Box, { marginBottom: 1 }, React.createElement(Text, { bold: true, color: "cyan" }, "\uD83D\uDE80 Aura CLI"), React.createElement(Text, { dimColor: true }, " - Type /help for commands")), error && (React.createElement(Box, { marginBottom: 1 }, React.createElement(Alert, { variant: "error" }, error))), suggestions.length > 0 && (React.createElement(Box, { marginBottom: 1, flexDirection: "column" }, React.createElement(Text, { dimColor: true }, "Suggestions:"), suggestions.map((suggestion) => (React.createElement(Text, { key: suggestion, color: "gray" }, " ", suggestion))))), React.createElement(Box, null, React.createElement(Text, { color: "green" }, "\u276F "), React.createElement(TextInput, { key: `input-${historyIndex}`, defaultValue: inputValue, onChange: (value) => setInputValue(value), onSubmit: handleCommand, placeholder: "Type a command (e.g., /init)", suggestions: suggestions })), commandHistory.length > 0 && (React.createElement(Box, { marginTop: 1 }, React.createElement(Text, { dimColor: true }, "\u2191\u2193 to navigate history \u2022 Ctrl+C to exit"))))); } } }