1
0
Fork 0
eos-downloader/eos_downloader/cli/get/commands.py
Daniel Baumann 8d2f70e3c7
Merging upstream version 0.12.0.
Signed-off-by: Daniel Baumann <daniel@debian.org>
2025-02-10 06:39:52 +01:00

386 lines
9.8 KiB
Python

#!/usr/bin/env python
# coding: utf-8 -*-
# pylint: disable=no-value-for-parameter
# pylint: disable=too-many-arguments
# pylint: disable=too-many-positional-arguments
# pylint: disable=line-too-long
# pylint: disable=redefined-builtin
# pylint: disable=broad-exception-caught
# flake8: noqa E501
"""CLI commands for listing Arista package information."""
import os
from typing import Union
import click
from eos_downloader.models.data import RTYPE_FEATURE
from eos_downloader.logics.download import SoftManager
from eos_downloader.logics.arista_server import AristaServer
from eos_downloader.logics.arista_xml_server import (
EosXmlObject,
AristaXmlQuerier,
CvpXmlObject,
)
from .utils import initialize, search_version, download_files, handle_docker_import
@click.command()
@click.option("--format", default="vmdk", help="Image format", show_default=True)
@click.option(
"--output",
default=str(os.path.relpath(os.getcwd(), start=os.curdir)),
help="Path to save image",
type=click.Path(),
show_default=True,
show_envvar=True,
)
@click.option(
"--latest",
is_flag=True,
help="Get latest version. If --branch is not use, get the latest branch with specific release type",
default=False,
show_envvar=True,
)
@click.option(
"--eve-ng",
is_flag=True,
help="Run EVE-NG vEOS provisioning (only if CLI runs on an EVE-NG server)",
default=False,
show_envvar=True,
)
@click.option(
"--import-docker",
is_flag=True,
help="Import docker image to local docker",
default=False,
show_envvar=True,
)
@click.option(
"--skip-download",
is_flag=True,
help="Skip download process - for debug only",
default=False,
)
@click.option(
"--docker-name",
default="arista/ceos",
help="Docker image name",
show_default=True,
show_envvar=True,
)
@click.option(
"--docker-tag",
default=None,
help="Docker image tag",
show_default=True,
show_envvar=True,
)
@click.option(
"--version",
default=None,
help="EOS version to download",
show_default=True,
show_envvar=True,
)
@click.option(
"--release-type",
default=RTYPE_FEATURE,
help="Release type (M for Maintenance, F for Feature)",
show_default=True,
show_envvar=True,
)
@click.option(
"--branch",
default=None,
help="Branch to download",
show_default=True,
show_envvar=True,
)
@click.option(
"--dry-run",
is_flag=True,
help="Enable dry-run mode: only run code without system changes",
default=False,
)
@click.pass_context
def eos(
ctx: click.Context,
format: str,
output: str,
eve_ng: bool,
import_docker: bool,
skip_download: bool,
docker_name: str,
docker_tag: str,
version: Union[str, None],
release_type: str,
latest: bool,
branch: Union[str, None],
dry_run: bool,
) -> int:
"""Download EOS image from Arista server."""
# pylint: disable=unused-variable
console, token, debug, log_level = initialize(ctx)
version = search_version(
console, token, version, latest, branch, format, release_type
)
if version is None:
raise ValueError("Version is not set correctly")
try:
eos_dl_obj = EosXmlObject(
searched_version=version, token=token, image_type=format
)
except Exception:
console.print_exception(show_locals=True)
return 1
cli = SoftManager(dry_run=dry_run)
if not skip_download:
if not eve_ng:
download_files(
console, cli, eos_dl_obj, output, rich_interface=True, debug=debug
)
else:
try:
cli.provision_eve(eos_dl_obj, noztp=True)
except Exception as e:
if debug:
console.print_exception(show_locals=True)
else:
console.print(f"\n[red]Exception raised: {e}[/red]")
return 1
if import_docker:
return handle_docker_import(
console, cli, eos_dl_obj, output, docker_name, docker_tag, debug
)
return 0
@click.command()
@click.option(
"--format",
default="ova",
help="Image format",
show_default=True,
show_envvar=True,
)
@click.option(
"--output",
default=str(os.path.relpath(os.getcwd(), start=os.curdir)),
help="Path to save image",
type=click.Path(),
show_default=True,
show_envvar=True,
)
@click.option(
"--latest",
is_flag=True,
help="Get latest version. If --branch is not use, get the latest branch with specific release type",
default=False,
show_envvar=True,
)
@click.option(
"--version",
default=None,
help="EOS version to download",
show_default=True,
show_envvar=True,
)
@click.option(
"--branch",
default=None,
help="Branch to download",
show_default=True,
show_envvar=True,
)
@click.option(
"--dry-run",
is_flag=True,
help="Enable dry-run mode: only run code without system changes",
default=False,
)
@click.pass_context
def cvp(
ctx: click.Context,
latest: bool,
format: str,
output: str,
version: Union[str, None],
branch: Union[str, None],
dry_run: bool = False,
) -> int:
"""Download CVP image from Arista server."""
# pylint: disable=unused-variable
console, token, debug, log_level = initialize(ctx)
if version is not None:
console.print(
f"Searching for EOS version [green]{version}[/green] for [blue]{format}[/blue] format..."
)
elif latest:
console.print(
f"Searching for [blue]latest[/blue] EOS version for [blue]{format}[/blue] format..."
)
elif branch is not None:
console.print(
f"Searching for EOS [b]latest[/b] version for [blue]{branch}[/blue] branch for [blue]{format}[/blue] format..."
)
if branch is not None or latest:
try:
querier = AristaXmlQuerier(token=token)
version_obj = querier.latest(package="cvp", branch=branch)
version = str(version_obj)
except Exception as e:
console.print(f"Token is set to: {token}")
console.print_exception(show_locals=True)
return 1
console.print(f"version to download is {version}")
if version is None:
raise ValueError("Version is not set correctly")
try:
cvp_dl_obj = CvpXmlObject(
searched_version=version, token=token, image_type=format
)
except Exception as e:
if debug:
console.print_exception(show_locals=True)
else:
console.print(f"\n[red]Exception raised: {e}[/red]")
return 1
cli = SoftManager(dry_run=dry_run)
download_files(
console,
cli,
cvp_dl_obj,
output,
rich_interface=True,
debug=debug,
checksum_format="md5sum",
)
console.print(f"CVP file is saved under: {output}")
return 0
@click.command()
@click.option(
"--source",
"-s",
help="Image path to download from Arista Website",
type=str,
show_default=False,
show_envvar=False,
)
@click.option(
"--output",
"-o",
default=str(os.path.relpath(os.getcwd(), start=os.curdir)),
help="Path to save downloaded package",
type=click.Path(),
show_default=True,
show_envvar=True,
)
@click.option(
"--import-docker",
is_flag=True,
help="Import docker image to local docker",
default=False,
show_envvar=True,
)
@click.option(
"--docker-name",
default="arista/ceos:raw",
help="Docker image name",
show_default=True,
show_envvar=True,
)
@click.option(
"--docker-tag",
default="dev",
help="Docker image tag",
show_default=True,
show_envvar=True,
)
@click.pass_context
# pylint: disable=too-many-branches
def path(
ctx: click.Context,
output: str,
source: str,
import_docker: bool,
docker_name: str,
docker_tag: str,
) -> int:
"""Download image from Arista server using direct path."""
console, token, debug, log_level = initialize(ctx)
if source is None:
console.print("[red]Source is not set correctly ![/red]")
return 1
filename = os.path.basename(source)
console.print(f"Downloading file {filename} from source: {source}")
console.print(f"Saving file to: {output}")
ar_server = AristaServer(token=token)
try:
file_url = ar_server.get_url(source)
if log_level == "debug":
console.print(f"URL to download file is: {file_url}")
except Exception as e:
if debug:
console.print_exception(show_locals=True)
else:
console.print(f"\n[red]Exception raised: {e}[/red]")
return 1
if file_url is None:
console.print("File URL is set to None when we expect a string")
return 1
cli = SoftManager(dry_run=False)
try:
cli.download_file(file_url, output, filename=filename)
except Exception as e:
if debug:
console.print_exception(show_locals=True)
else:
console.print(f"\n[red]Exception raised: {e}[/red]")
return 1
if import_docker:
console.print(
f"Importing docker image [green]{docker_name}:{docker_tag}[/green] from [blue]{os.path.join(output, filename)}[/blue]..."
)
try:
cli.import_docker(
local_file_path=os.path.join(output, filename),
docker_name=docker_name,
docker_tag=docker_tag,
)
except FileNotFoundError:
if debug:
console.print_exception(show_locals=True)
else:
console.print(
f"\n[red]File not found: {os.path.join(output, filename)}[/red]"
)
return 1
console.print(
f"Docker image imported successfully: [green]{docker_name}:{docker_tag}[/green]"
)
return 0