improved env loading
This commit is contained in:
parent
7c82226ff9
commit
41a21671ca
101
groove/cli.py
101
groove/cli.py
|
@ -1,21 +1,36 @@
|
|||
import logging
|
||||
import os
|
||||
import sys
|
||||
import typer
|
||||
|
||||
from pathlib import Path
|
||||
from typing import Optional
|
||||
from textwrap import dedent
|
||||
|
||||
from dotenv import load_dotenv
|
||||
from rich import print
|
||||
from rich.logging import RichHandler
|
||||
|
||||
import groove.path
|
||||
|
||||
from groove.shell import interactive_shell
|
||||
from groove.db.manager import database_manager
|
||||
from groove.webserver import webserver
|
||||
from groove.exceptions import ConfigurationError
|
||||
from groove.console import Console
|
||||
|
||||
app = typer.Typer()
|
||||
|
||||
|
||||
def initialize():
|
||||
load_dotenv()
|
||||
@app.callback()
|
||||
def main(
|
||||
context: typer.Context,
|
||||
env: Optional[Path] = typer.Option(
|
||||
Path('~/.groove'),
|
||||
help="Path to the Groove on Demand environment",
|
||||
)
|
||||
):
|
||||
load_dotenv(env.expanduser())
|
||||
debug = os.getenv('DEBUG', None)
|
||||
logging.basicConfig(
|
||||
format='%(message)s',
|
||||
|
@ -26,13 +41,76 @@ def initialize():
|
|||
)
|
||||
logging.getLogger('asyncio').setLevel(logging.ERROR)
|
||||
|
||||
try:
|
||||
groove.path.media_root()
|
||||
groove.path.static_root()
|
||||
groove.path.themes_root()
|
||||
groove.path.database()
|
||||
except ConfigurationError as e:
|
||||
sys.stderr.write(f'{e}\n')
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
@app.command()
|
||||
def list():
|
||||
def setup(context: typer.Context):
|
||||
"""
|
||||
List all Playlists
|
||||
(Re)Initialize Groove on Demand.
|
||||
"""
|
||||
print(dedent(
|
||||
"""
|
||||
Interactive setup is not yet available. Sorry!
|
||||
|
||||
In the mean time, please make sure you set MEDIA_ROOT and SECRET_KEY
|
||||
in your environment. By default, Groove on Demand will attempt to load
|
||||
these variables from ~/.groove, which may contain the following
|
||||
variables as well. See also the --env paramter.
|
||||
|
||||
# Set this one. The path containing your media files
|
||||
MEDIA_ROOT=
|
||||
|
||||
# the kinds of files to import
|
||||
# MEDIA_GLOB=*.mp3,*.flac,*.m4a
|
||||
|
||||
# where to store the groove_on_demand.db sqlite database.
|
||||
# DATABASE_PATH=~
|
||||
|
||||
# Try 'groove themes' to see a list of available themes.
|
||||
# DEFAULT_THEME=blue_train
|
||||
|
||||
# Web interface configuration
|
||||
# HOST=127.0.0.1
|
||||
# PORT=2323
|
||||
|
||||
# Set this to a suitably random string.
|
||||
SECRET_KEY=much secret very private
|
||||
|
||||
# Console configuration
|
||||
# EDITOR=
|
||||
# CONSOLE_WIDTH=auto
|
||||
"""
|
||||
))
|
||||
|
||||
|
||||
@app.command()
|
||||
def themes(context: typer.Context):
|
||||
"""
|
||||
List the available themes.
|
||||
"""
|
||||
print("Available themes:")
|
||||
themes = [theme for theme in groove.path.themes_root().iterdir()]
|
||||
tags = ('artist', 'title', 'bold', 'dim', 'link', 'prompt', 'bright', 'text', 'help')
|
||||
for theme in themes:
|
||||
text = ''
|
||||
for tag in tags:
|
||||
text += f'[{tag}]◼◼◼◼◼◼'
|
||||
Console(theme=theme.name).print(f' ▪ [title]{theme.name}[/title] {text}')
|
||||
|
||||
|
||||
@app.command()
|
||||
def playlists(context: typer.Context):
|
||||
"""
|
||||
List all playlists
|
||||
"""
|
||||
initialize()
|
||||
with database_manager() as manager:
|
||||
shell = interactive_shell.InteractiveShell(manager)
|
||||
shell.list(None)
|
||||
|
@ -40,6 +118,7 @@ def list():
|
|||
|
||||
@app.command()
|
||||
def scan(
|
||||
context: typer.Context,
|
||||
path: Optional[Path] = typer.Option(
|
||||
'',
|
||||
help="A path to scan, relative to your MEDIA_ROOT. "
|
||||
|
@ -49,7 +128,6 @@ def scan(
|
|||
"""
|
||||
Scan the filesystem and create track entries in the database.
|
||||
"""
|
||||
initialize()
|
||||
with database_manager() as manager:
|
||||
shell = interactive_shell.InteractiveShell(manager)
|
||||
shell.console.print("Starting the Groove on Demand scanner...")
|
||||
|
@ -57,13 +135,17 @@ def scan(
|
|||
|
||||
|
||||
@app.command()
|
||||
def shell():
|
||||
initialize()
|
||||
interactive_shell.start()
|
||||
def shell(context: typer.Context):
|
||||
"""
|
||||
Start the Groove on Demand interactive shell.
|
||||
"""
|
||||
with database_manager() as manager:
|
||||
interactive_shell.InteractiveShell(manager).start()
|
||||
|
||||
|
||||
@app.command()
|
||||
def server(
|
||||
context: typer.Context,
|
||||
host: str = typer.Argument(
|
||||
'0.0.0.0',
|
||||
help="bind address",
|
||||
|
@ -80,7 +162,6 @@ def server(
|
|||
"""
|
||||
Start the Groove on Demand playlsit server.
|
||||
"""
|
||||
initialize()
|
||||
with database_manager() as manager:
|
||||
manager.import_from_filesystem()
|
||||
webserver.start(host=host, port=port, debug=debug)
|
||||
|
|
|
@ -26,7 +26,7 @@ BASE_STYLE = {
|
|||
}
|
||||
|
||||
|
||||
def console_theme(theme_name: Union[str, None] = None) -> dict:
|
||||
def console_theme(theme_name: Union[str, None] = 'blue_train') -> dict:
|
||||
"""
|
||||
Return a console theme as a dictionary.
|
||||
|
||||
|
@ -36,8 +36,8 @@ def console_theme(theme_name: Union[str, None] = None) -> dict:
|
|||
cfg = ConfigParser()
|
||||
cfg.read_dict({'styles': BASE_STYLE})
|
||||
cfg.read(theme(
|
||||
theme_name or os.environ['DEFAULT_THEME']) / Path('console.cfg')
|
||||
)
|
||||
Path(theme_name or os.environ['DEFAULT_THEME']) / Path('console.cfg')
|
||||
))
|
||||
return cfg['styles']
|
||||
|
||||
|
||||
|
|
|
@ -69,7 +69,7 @@ class MediaScanner:
|
|||
console: Union[Console, None] = None,
|
||||
) -> None:
|
||||
self._db = db
|
||||
self._glob = tuple((glob or os.environ.get('MEDIA_GLOB')).split(','))
|
||||
self._glob = tuple((glob or os.environ.get('MEDIA_GLOB', '*.mp3,*.flac,*.m4a')).split(','))
|
||||
self._root = groove.path.media_root()
|
||||
self._console = console or Console()
|
||||
self._scanned = 0
|
||||
|
|
|
@ -4,14 +4,14 @@ import os
|
|||
from pathlib import Path
|
||||
from groove.exceptions import ConfigurationError, ThemeMissingException, ThemeConfigurationError
|
||||
|
||||
_setup_hint = "You may be able to solve this error by running 'groove setup'."
|
||||
_setup_hint = "You may be able to solve this error by running 'groove setup' or specifying the --env parameter."
|
||||
_reinstall_hint = "You might need to reinstall Groove On Demand to fix this error."
|
||||
|
||||
|
||||
def root():
|
||||
path = os.environ.get('GROOVE_ON_DEMAND_ROOT', None)
|
||||
if not path:
|
||||
raise ConfigurationError(f"GROOVE_ON_DEMAND_ROOT is not defined in your environment.\n\n{_setup_hint}")
|
||||
raise ConfigurationError(f"GROOVE_ON_DEMAND_ROOT is not defined in your environment.\n{_setup_hint}")
|
||||
path = Path(path).expanduser()
|
||||
if not path.exists() or not path.is_dir():
|
||||
raise ConfigurationError(
|
||||
|
@ -83,7 +83,7 @@ def themes_root():
|
|||
|
||||
def theme(name):
|
||||
path = themes_root() / Path(name)
|
||||
if not path.exists() or not path.is_dir():
|
||||
if not path.exists():
|
||||
available = ','.join(available_themes())
|
||||
raise ThemeMissingException(
|
||||
f"A theme directory named {name} does not exist or isn't a directory. "
|
||||
|
@ -102,13 +102,9 @@ def available_themes():
|
|||
|
||||
|
||||
def database():
|
||||
path = os.environ.get('DATABASE_PATH', None)
|
||||
if not path:
|
||||
path = root()
|
||||
else: # pragma: no cover
|
||||
path = Path(path).expanduser()
|
||||
if not path.exists() or not path.is_dir():
|
||||
raise ConfigurationError(
|
||||
"DATABASE_PATH doesn't exist or isn't a directory.\n\n{_setup_hint}"
|
||||
)
|
||||
path = Path(os.environ.get('DATABASE_PATH', '~')).expanduser()
|
||||
if not path.exists() or not path.is_dir():
|
||||
raise ConfigurationError(
|
||||
"DATABASE_PATH doesn't exist or isn't a directory.\n\n{_setup_hint}"
|
||||
)
|
||||
return path / Path('groove_on_demand.db')
|
||||
|
|
|
@ -16,7 +16,7 @@ from groove.webserver import requests, themes
|
|||
server = bottle.Bottle()
|
||||
|
||||
|
||||
def start(host: str, port: int, debug: bool) -> None: # pragma: no cover
|
||||
def start(host: str = '127.0.0.1', port: int = 2323, debug: bool = False) -> None: # pragma: no cover
|
||||
"""
|
||||
Start the Bottle app.
|
||||
"""
|
||||
|
|
|
@ -35,7 +35,7 @@ def test_theme_no_path():
|
|||
|
||||
|
||||
def test_database_default(env):
|
||||
assert path.database().relative_to(path.root())
|
||||
assert path.database()
|
||||
|
||||
|
||||
def test_database(env):
|
||||
|
|
Loading…
Reference in New Issue
Block a user