mirror of
https://github.com/Textualize/textual.git
synced 2025-10-17 02:38:12 +03:00
126 lines
3.2 KiB
Python
126 lines
3.2 KiB
Python
from __future__ import annotations
|
|
|
|
|
|
import click
|
|
from importlib_metadata import version
|
|
|
|
from textual.pilot import Pilot
|
|
from textual._import_app import import_app, AppFail
|
|
|
|
|
|
@click.group()
|
|
@click.version_option(version("textual"))
|
|
def run():
|
|
pass
|
|
|
|
|
|
@run.command(help="Run the Textual Devtools console.")
|
|
@click.option("-v", "verbose", help="Enable verbose logs.", is_flag=True)
|
|
@click.option("-x", "--exclude", "exclude", help="Exclude log group(s)", multiple=True)
|
|
def console(verbose: bool, exclude: list[str]) -> None:
|
|
"""Launch the textual console."""
|
|
from rich.console import Console
|
|
from textual.devtools.server import _run_devtools
|
|
|
|
console = Console()
|
|
console.clear()
|
|
console.show_cursor(False)
|
|
try:
|
|
_run_devtools(verbose=verbose, exclude=exclude)
|
|
finally:
|
|
console.show_cursor(True)
|
|
|
|
|
|
@run.command(
|
|
"run",
|
|
context_settings={
|
|
"ignore_unknown_options": True,
|
|
},
|
|
)
|
|
@click.argument("import_name", metavar="FILE or FILE:APP")
|
|
@click.option("--dev", "dev", help="Enable development mode", is_flag=True)
|
|
@click.option("--press", "press", help="Comma separated keys to simulate press")
|
|
def run_app(import_name: str, dev: bool, press: str) -> None:
|
|
"""Run a Textual app.
|
|
|
|
The code to run may be given as a path (ending with .py) or as a Python
|
|
import, which will load the code and run an app called "app". You may optionally
|
|
add a colon plus the class or class instance you want to run.
|
|
|
|
Here are some examples:
|
|
|
|
textual run foo.py
|
|
|
|
textual run foo.py:MyApp
|
|
|
|
textual run module.foo
|
|
|
|
textual run module.foo:MyApp
|
|
|
|
If you are running a file and want to pass command line arguments, wrap the filename and arguments
|
|
in quotes:
|
|
|
|
textual run "foo.py arg --option"
|
|
|
|
"""
|
|
|
|
import os
|
|
import sys
|
|
|
|
from textual.features import parse_features
|
|
|
|
features = set(parse_features(os.environ.get("TEXTUAL", "")))
|
|
if dev:
|
|
features.add("debug")
|
|
features.add("devtools")
|
|
|
|
os.environ["TEXTUAL"] = ",".join(sorted(features))
|
|
try:
|
|
app = import_app(import_name)
|
|
except AppFail as error:
|
|
from rich.console import Console
|
|
|
|
console = Console(stderr=True)
|
|
console.print(str(error))
|
|
sys.exit(1)
|
|
|
|
press_keys = press.split(",") if press else None
|
|
|
|
async def run_press_keys(pilot: Pilot) -> None:
|
|
if press_keys is not None:
|
|
await pilot.press(*press_keys)
|
|
|
|
result = app.run(auto_pilot=run_press_keys)
|
|
|
|
if result is not None:
|
|
from rich.console import Console
|
|
from rich.pretty import Pretty
|
|
|
|
console = Console()
|
|
console.print("[b]The app returned:")
|
|
console.print(Pretty(result))
|
|
|
|
|
|
@run.command("borders")
|
|
def borders():
|
|
"""Explore the border styles available in Textual."""
|
|
from textual.cli.previews import borders
|
|
|
|
borders.app.run()
|
|
|
|
|
|
@run.command("easing")
|
|
def easing():
|
|
"""Explore the animation easing functions available in Textual."""
|
|
from textual.cli.previews import easing
|
|
|
|
easing.app.run()
|
|
|
|
|
|
@run.command("colors")
|
|
def colors():
|
|
"""Explore the design system."""
|
|
from textual.cli.previews import colors
|
|
|
|
colors.app.run()
|