Skip to content

Commit

Permalink
expose.web setting
Browse files Browse the repository at this point in the history
  • Loading branch information
dvolodin7 committed Mar 2, 2025
1 parent 8130017 commit 616d5d9
Show file tree
Hide file tree
Showing 8 changed files with 116 additions and 21 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,11 @@ To see unreleased changes, please see the [CHANGELOG on the master branch](https
### Added

* Kafka flushes every message on single-node installations.
* `expose.web` setting.

### Changed

* `expose.port` replaced with `expose.web.port` settings.

### Infrastructure

Expand Down
8 changes: 5 additions & 3 deletions docs/reference/config.md
Original file line number Diff line number Diff line change
Expand Up @@ -98,13 +98,15 @@ expose:
domain_name: go.getnoc.com
```

### port { #expose-port }
### web { #expose-web }

Web interface port. `32777` is used by default.
Web interface address and port.

```
expose:
port: 32777
web:
address: 127.0.0.1
port: 32777
```
### open_browser { #expose-open-browser }
Expand Down
8 changes: 3 additions & 5 deletions src/gufo/thor/cli.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# ---------------------------------------------------------------------
# Gufo Thor: Command-line utility
# ---------------------------------------------------------------------
# Copyright (C) 2023, Gufo Labs
# Copyright (C) 2023-25, Gufo Labs
# ---------------------------------------------------------------------
"""
`gufo-thor` command-line utility.
Expand Down Expand Up @@ -193,8 +193,8 @@ def _get_ui_url(self: "Cli") -> str:
"""
cfg = self.config
parts = ["https://", cfg.expose.domain_name]
if cfg.expose.port != DEFAULT_HTTPS_PORT:
parts.append(f":{cfg.expose.port}")
if cfg.expose.web and cfg.expose.web.port != DEFAULT_HTTPS_PORT:
parts.append(f":{cfg.expose.web.port}")
parts.append("/")
return "".join(parts)

Expand All @@ -205,7 +205,6 @@ def handle_up(self: "Cli", ns: argparse.Namespace) -> ExitCode:
self.config.noc.migrate = True
elif ns.no_migrate:
self.config.noc.migrate = False
#
r = self.handle_prepare(ns)
if r != ExitCode.OK:
return r
Expand All @@ -223,7 +222,6 @@ def handle_up(self: "Cli", ns: argparse.Namespace) -> ExitCode:
logger.warning(
"Cannot start browser. Command `open` is not found"
)
#
return ExitCode.OK

def handle_stop(self: "Cli", ns: argparse.Namespace) -> ExitCode:
Expand Down
97 changes: 91 additions & 6 deletions src/gufo/thor/config.py
Original file line number Diff line number Diff line change
@@ -1,18 +1,26 @@
# ---------------------------------------------------------------------
# Gufo Thor: Command-line utility
# ---------------------------------------------------------------------
# Copyright (C) 2023, Gufo Labs
# Copyright (C) 2023-25, Gufo Labs
# ---------------------------------------------------------------------
"""Config data structures."""

# Python Modules
from dataclasses import dataclass
from importlib import resources
from typing import Any, Dict, Literal, Optional
from typing import Any, Dict, Literal, Optional, Union

# Third-party modules
import yaml

# Gufo Thor modules
from .log import logger

LOCALHOST = "127.0.0.1"
ALL = "0.0.0.0"

DEFAULT_WEB_PORT = 32777


@dataclass
class NocConfig(object):
Expand Down Expand Up @@ -54,6 +62,65 @@ def from_dict(data: Dict[str, Any]) -> "NocConfig":
return NocConfig(**data)


@dataclass
class Listen(object):
"""
Listener configuration.
Used to proxy host's ports into the container.
Accepts formats:
```
* <port>
* "<port>"
* "<address>:<port>"
* {"port": <port>}
* {"address": "<address>", "port": <port>}
```
Attributes:
address: Listen address.
port: Listen port.
"""

address: str
port: int

@staticmethod
def from_dict(data: Union[dict[str, Any], int, str]) -> "Listen":
"""
Generate listener from data.
Args:
data: Incoming data.
Returns:
A configured Listener instance.
"""
if isinstance(data, int):
return Listen(address=LOCALHOST, port=data)
if isinstance(data, str):
if ":" in data:
addr, port = data.rsplit(":", 1)
return Listen(address=addr, port=int(port))
return Listen(address=LOCALHOST, port=int(data))
return Listen(
address=data.get("address", LOCALHOST), port=data["port"]
)

def docker_compose_port(self: "Listen", container_port: int) -> str:
"""
Generate configuration for port forwarding.
Args:
container_port: Port in the container.
Returns:
Port configuration for docker compose.
"""
return f"{self.address}:{self.port}:{container_port}"


@dataclass
class ExposeConfig(object):
"""
Expand All @@ -62,11 +129,13 @@ class ExposeConfig(object):
Attributes:
domain_name: A domain name through which the NOC's user interface
will be accessed in browser.
port: An HTTPS port of the NOC's user interface.
web: Web listener configuration.
port: An HTTPS port of the NOC's user interface (deprecated).
open_browser: Open browser on startup.
"""

domain_name: str = "go.getnoc.com"
port: int = 32777
web: Optional[Listen] = None
open_browser: bool = True

@staticmethod
Expand All @@ -75,11 +144,27 @@ def from_dict(data: Dict[str, Any]) -> "ExposeConfig":
Generate ExposeConfig instance from a dictionary.
Args:
data: Incoming data.
data: Incoming data.
Returns:
A configured ExposeConfig instance.
A configured ExposeConfig instance.
"""
data = data.copy()
# Decode web
if "web" in data:
data["web"] = Listen.from_dict(data["web"])
elif "port" in data:
data["web"] = Listen.from_dict(data["port"])
else:
data["web"] = Listen(address=LOCALHOST, port=DEFAULT_WEB_PORT)
# Deprecated port option
if data.get("port"):
port = data.pop("port")
logger.warning("Using obsolete `expose.port` configuration.")
logger.warning("In thor.yml replace:")
logger.warning(">>>>>\nexpose:\n port: %s\n<<<<<", port)
logger.warning("with:")
logger.warning(">>>>>\nexpose:\n web:\n port: %s\n<<<<<", port)
return ExposeConfig(**data)


Expand Down
3 changes: 2 additions & 1 deletion src/gufo/thor/samples/common.yml
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ noc:
theme: noc
expose:
domain_name: go.getnoc.com
port: 32777
web:
port: 32777
open_browser: true
services: [web, card, discovery, activator, classifier, correlator, ping, shell]
3 changes: 2 additions & 1 deletion src/gufo/thor/samples/simple.yml
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ noc:
theme: noc
expose:
domain_name: go.getnoc.com
port: 32777
web:
port: 32777
open_browser: true
services: [web, card, shell]
10 changes: 6 additions & 4 deletions src/gufo/thor/services/envoy.py
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# ---------------------------------------------------------------------
# Gufo Thor: envoy service
# ---------------------------------------------------------------------
# Copyright (C) 2023-24, Gufo Labs
# Copyright (C) 2023-25, Gufo Labs
# ---------------------------------------------------------------------
"""
envoy service.
Expand Down Expand Up @@ -109,7 +109,9 @@ def get_compose_ports(
self: "EnvoyService", config: Config, svc: Optional[ServiceConfig]
) -> Optional[List[str]]:
"""Get ports section."""
return [f"{config.expose.port}:443"]
if config.expose.web:
return [config.expose.web.docker_compose_port(443)]
return None

def prepare_compose_config(
self: "EnvoyService",
Expand All @@ -119,11 +121,11 @@ def prepare_compose_config(
) -> None:
"""Generate config."""
# Generate domain_name_and_port
if config.expose.port == HTTPS:
if not config.expose.web or config.expose.web.port == HTTPS:
domain_name_and_port = config.expose.domain_name
else:
domain_name_and_port = (
f"{config.expose.domain_name}:{config.expose.port}"
f"{config.expose.domain_name}:{config.expose.web.port}"
)
# Generate routes
routes: List[Route] = []
Expand Down
3 changes: 2 additions & 1 deletion tests/test_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,8 @@ def test_simple() -> None:
assert cfg.noc.path is None
assert cfg.noc.custom is None
assert cfg.expose.domain_name == "go.getnoc.com"
assert cfg.expose.port == 32777
assert cfg.expose.web
assert cfg.expose.web.port == 32777
assert len(cfg.services) == 3
assert "web" in cfg.services
assert "card" in cfg.services

0 comments on commit 616d5d9

Please sign in to comment.