Initial upload: shell-speak CLI tool with natural language to shell command conversion
This commit is contained in:
122
shell_speak/output.py
Normal file
122
shell_speak/output.py
Normal file
@@ -0,0 +1,122 @@
|
||||
"""Output formatting with Rich."""
|
||||
|
||||
from typing import Optional
|
||||
|
||||
from rich.console import Console
|
||||
from rich.panel import Panel
|
||||
from rich.syntax import Syntax
|
||||
from rich.text import Text
|
||||
from rich.theme import Theme
|
||||
|
||||
from shell_speak.models import CommandMatch, HistoryEntry
|
||||
from shell_speak.nlp import tokenize
|
||||
|
||||
|
||||
custom_theme = Theme({
|
||||
"command": "bold cyan",
|
||||
"keyword": "bold green",
|
||||
"tool": "bold magenta",
|
||||
"explanation": "italic",
|
||||
"error": "bold red",
|
||||
"warning": "yellow",
|
||||
"success": "bold green",
|
||||
"info": "blue",
|
||||
})
|
||||
|
||||
|
||||
console = Console(theme=custom_theme)
|
||||
|
||||
|
||||
def display_command(match: CommandMatch, explain: bool = False) -> None:
|
||||
"""Display a command match with rich formatting."""
|
||||
syntax = Syntax(match.command, "bash", theme="monokai", line_numbers=False)
|
||||
|
||||
title = f"[tool]{match.pattern.tool}[/tool] command"
|
||||
panel = Panel(
|
||||
syntax,
|
||||
title=title,
|
||||
expand=False,
|
||||
border_style="cyan",
|
||||
)
|
||||
console.print(panel)
|
||||
|
||||
if explain or match.confidence < 0.8:
|
||||
confidence_pct = int(match.confidence * 100)
|
||||
confidence_color = "success" if match.confidence >= 0.8 else "warning" if match.confidence >= 0.5 else "error"
|
||||
console.print(f"Confidence: [{confidence_color}]{confidence_pct}%[/]")
|
||||
|
||||
if match.explanation:
|
||||
console.print(f"\n[explanation]{match.explanation}[/]")
|
||||
|
||||
if explain:
|
||||
_show_detailed_explanation(match)
|
||||
|
||||
|
||||
def _show_detailed_explanation(match: CommandMatch) -> None:
|
||||
"""Show detailed breakdown of a command."""
|
||||
console.print("\n[info]Command breakdown:[/]")
|
||||
tokens = tokenize(match.command)
|
||||
|
||||
for token in tokens:
|
||||
if token in ("docker", "kubectl", "git", "ls", "cd", "cat", "grep", "find", "rm", "cp", "mv"):
|
||||
console.print(f" [keyword]{token}[/]", end=" ")
|
||||
else:
|
||||
console.print(f" {token}", end=" ")
|
||||
|
||||
|
||||
def display_error(message: str) -> None:
|
||||
"""Display an error message."""
|
||||
console.print(f"[error]Error:[/] {message}")
|
||||
|
||||
|
||||
def display_warning(message: str) -> None:
|
||||
"""Display a warning message."""
|
||||
console.print(f"[warning]Warning:[/] {message}")
|
||||
|
||||
|
||||
def display_info(message: str) -> None:
|
||||
"""Display an info message."""
|
||||
console.print(f"[info]{message}[/]")
|
||||
|
||||
|
||||
def display_history(entries: list[HistoryEntry], limit: int = 20) -> None:
|
||||
"""Display command history."""
|
||||
console.print(f"\n[info]Command History (last {limit}):[/]\n")
|
||||
|
||||
for i, entry in enumerate(entries[-limit:], 1):
|
||||
timestamp = entry.timestamp.strftime("%Y-%m-%d %H:%M")
|
||||
console.print(f"{i}. [tool]{entry.tool}[/tool] | {timestamp}")
|
||||
console.print(f" Query: {entry.query}")
|
||||
console.print(f" [command]{entry.command}[/]")
|
||||
console.print()
|
||||
|
||||
|
||||
def display_suggestions(suggestions: list[str]) -> None:
|
||||
"""Display command suggestions."""
|
||||
if not suggestions:
|
||||
return
|
||||
|
||||
console.print("\n[info]Did you mean?[/]")
|
||||
for i, suggestion in enumerate(suggestions[:5], 1):
|
||||
console.print(f" {i}. {suggestion}")
|
||||
|
||||
|
||||
def display_learn_success(query: str, command: str) -> None:
|
||||
"""Display confirmation of learning."""
|
||||
console.print(f"[success]Learned new command:[/]")
|
||||
console.print(f" Query: {query}")
|
||||
console.print(f" [command]{command}[/]")
|
||||
|
||||
|
||||
def display_forget_success(query: str) -> None:
|
||||
"""Display confirmation of forgetting a pattern."""
|
||||
console.print(f"[success]Forgot pattern for:[/] {query}")
|
||||
|
||||
|
||||
def display_help_header() -> None:
|
||||
"""Display the help header."""
|
||||
console.print(Panel(
|
||||
Text("Shell Speak - Natural Language to Shell Commands", justify="center", style="bold cyan"),
|
||||
subtitle="Type a description of what you want to do",
|
||||
expand=False,
|
||||
))
|
||||
Reference in New Issue
Block a user