From 46e803a2c63e859e409c489dc6f1f14f4abc868e Mon Sep 17 00:00:00 2001 From: Alexander Guschin <1aguschin@gmail.com> Date: Wed, 17 May 2023 12:27:45 +0300 Subject: [PATCH] attempts to fix --- mlem/cli/deployment.py | 4 +++- mlem/contrib/flyio/meta.py | 45 +++++++++++++++++++++---------------- mlem/contrib/flyio/utils.py | 14 +++++++++++- tests/contrib/test_flyio.py | 10 ++++++++- 4 files changed, 51 insertions(+), 22 deletions(-) diff --git a/mlem/cli/deployment.py b/mlem/cli/deployment.py index 3bda0898..d0c889aa 100644 --- a/mlem/cli/deployment.py +++ b/mlem/cli/deployment.py @@ -145,7 +145,9 @@ def deploy_run_command( if not meta.is_state_empty: if not force: raise DeploymentError( - f"Different deployment meta already exists at {meta.loc}. Please use `mlem deployment run --load ...`" + f"The deployment file you specified ('{meta.loc.basename}') already describes a different deployment." + " Please add `--force` to overwrite it," + " or use `mlem deployment run --load ...` to reuse it." ) echo( EMOJI_STOP diff --git a/mlem/contrib/flyio/meta.py b/mlem/contrib/flyio/meta.py index fdf830a9..26c71ae4 100644 --- a/mlem/contrib/flyio/meta.py +++ b/mlem/contrib/flyio/meta.py @@ -113,28 +113,35 @@ def _create_app(self, state: FlyioAppState): args["access-token"] = self.get_env().access_token if self.org: args["org"] = self.org + port = getattr(self.server, "ui_port", None) or self.server.port + if port: + args["internal-port"] = port run_flyctl("launch", workdir=tempdir, kwargs=args) state.fly_toml = read_fly_toml(tempdir) - port = getattr(self.server, "port", None) or getattr( - self.server, "ui_port", None - ) - if port: # tell flyio to expose specific port + if getattr(self.server, "server_port", None): + fly_toml = parse(state.fly_toml) + fly_toml["services.ports"] = { + "handlers": ["http"], + "port": self.server.server_port, + "force_https": True, + } + state.fly_toml = fly_toml.as_string() + if getattr(self.server, "middlewares", None): + # set fly to collect metrics from prometheus if exposed fly_toml = parse(state.fly_toml) - fly_toml["services"][0]["internal_port"] = port - if self.server and self.server.middlewares: - # set fly to collect metrics from prometheus if exposed - from mlem.contrib.prometheus import ( # noqa - PrometheusFastAPIMiddleware, - ) - - if any( - isinstance(m, PrometheusFastAPIMiddleware) - for m in self.server.middlewares.__root__ - ): - fly_toml["metrics"] = { - "port": port, - "path": "/metrics", - } + from mlem.contrib.prometheus import ( # noqa + PrometheusFastAPIMiddleware, + ) + + if any( + isinstance(m, PrometheusFastAPIMiddleware) + for m in self.server.middlewares.__root__ + ): + fly_toml["metrics"] = { + "port": getattr(self.server, "server_port", None) + or self.server.port, + "path": "/metrics", + } state.fly_toml = fly_toml.as_string() status = get_status(workdir=tempdir) state.app_name = status.Name diff --git a/mlem/contrib/flyio/utils.py b/mlem/contrib/flyio/utils.py index 4200cf60..f7e720e8 100644 --- a/mlem/contrib/flyio/utils.py +++ b/mlem/contrib/flyio/utils.py @@ -1,4 +1,5 @@ import json +import logging import os.path import subprocess from typing import Any, Dict @@ -10,9 +11,20 @@ FLY_TOML = "fly.toml" +logger = logging.getLogger(__name__) + + def check_flyctl_exec(): try: - run_flyctl("version", wrap_error=False) + cmd = run_flyctl("version --json", wrap_error=False) + output = json.loads(cmd.decode()) + version = output.get("Version", None) + if not version or version.split(".")[1] != "1": + logger.warning( + "If flyio deployment is causing problems, the `flyctl` version may be the cause. " + f"You have {version} installed. Try to install `flyctl` 0.1.x." + ) + return output except subprocess.SubprocessError as e: raise DeploymentError( "flyctl executable is not available. Please install it using " diff --git a/tests/contrib/test_flyio.py b/tests/contrib/test_flyio.py index 8c0cdfec..aa2da1de 100644 --- a/tests/contrib/test_flyio.py +++ b/tests/contrib/test_flyio.py @@ -2,7 +2,15 @@ from unittest.mock import ANY, patch from mlem.contrib.flyio.meta import FlyioApp -from mlem.contrib.flyio.utils import FlyioStatusModel +from mlem.contrib.flyio.utils import FlyioStatusModel, check_flyctl_exec + + +def test_check_flyctl_exec(): + output = check_flyctl_exec() + version = output["Version"] + assert ( + version.split(".")[1] == "1" + ), f"flyctl version was bumped ({version} now), this may cause problems with deployment" def test_flyio_create_app(tmp_path: Path):