Problem
AbstractService currently contains Docker Compose specific fields and helpers even though services can target different backends such as Docker, Kubernetes, native, or connector-based integrations.
Examples in mlox/service.py:
target_docker_script
target_docker_env
compose_service_names
compose_up() / compose_down()
compose_service_status()
compose_service_log_tail()
- Docker Compose start/stop script generation in
dump_state()
This makes every service appear to have Docker/Compose runtime behavior, even when its declared backend is Kubernetes, native, or connector. With explicit service capabilities now separated from backend capabilities, the service base class should follow the same separation.
Proposed Direction
Introduce a backend/runtime-specific mixin or abstraction, for example:
DockerComposeServiceMixin
target_docker_script
target_docker_env
compose_service_names
compose_up()
compose_down()
compose_service_status()
compose_service_log_tail()
- Docker-specific runtime state dump hooks
Keep AbstractService focused on backend-agnostic service behavior:
- identity/config fields
- lifecycle contract:
setup, spin_up, spin_down, check, teardown
- secrets contract
- service URL/port registration
- executor binding
- dependency lookup
- generic state persistence
Compatibility Notes
This should be staged to avoid breaking existing Docker services and UI code.
Suggested migration:
- Add
DockerComposeServiceMixin while leaving existing behavior available.
- Update Docker-backed service classes to inherit the mixin explicitly.
- Update UI/use-case code to use
getattr(service, "compose_service_names", {}) or a generic runtime/log capability instead of assuming every service has Compose labels.
- Move Docker-specific methods and fields out of
AbstractService.
- Keep temporary compatibility shims only if needed for downstream callers/tests.
Acceptance Criteria
AbstractService no longer declares Docker/Compose-only fields or methods as part of the generic service contract.
- Docker-backed services still support Compose setup, start, stop, status, logs, and debug state output.
- Kubernetes, native, and connector services are not required to expose Docker/Compose fields.
- Existing service YAML loading remains backward compatible.
- UI/TUI/log views handle non-Compose services gracefully.
- Unit tests cover Docker Compose services and at least one non-Docker service without Compose attributes.
Problem
AbstractServicecurrently contains Docker Compose specific fields and helpers even though services can target different backends such as Docker, Kubernetes, native, or connector-based integrations.Examples in
mlox/service.py:target_docker_scripttarget_docker_envcompose_service_namescompose_up()/compose_down()compose_service_status()compose_service_log_tail()dump_state()This makes every service appear to have Docker/Compose runtime behavior, even when its declared backend is Kubernetes, native, or connector. With explicit service capabilities now separated from backend capabilities, the service base class should follow the same separation.
Proposed Direction
Introduce a backend/runtime-specific mixin or abstraction, for example:
DockerComposeServiceMixintarget_docker_scripttarget_docker_envcompose_service_namescompose_up()compose_down()compose_service_status()compose_service_log_tail()Keep
AbstractServicefocused on backend-agnostic service behavior:setup,spin_up,spin_down,check,teardownCompatibility Notes
This should be staged to avoid breaking existing Docker services and UI code.
Suggested migration:
DockerComposeServiceMixinwhile leaving existing behavior available.getattr(service, "compose_service_names", {})or a generic runtime/log capability instead of assuming every service has Compose labels.AbstractService.Acceptance Criteria
AbstractServiceno longer declares Docker/Compose-only fields or methods as part of the generic service contract.