Skip to content

Commit 9753357

Browse files
authored
Logoscore integration
* Logoscore: Add builders * Logoscore: experiment (#343)
1 parent 1cba42a commit 9753357

46 files changed

Lines changed: 2111 additions & 0 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

src/deployments/logos_core/__init__.py

Whitespace-only changes.
Lines changed: 187 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,187 @@
1+
# Python Imports
2+
from typing import List, Optional, Self
3+
4+
from kubernetes.client import (
5+
V1ContainerPort,
6+
V1EnvVar,
7+
V1EnvVarSource,
8+
V1ObjectFieldSelector,
9+
V1ObjectMeta,
10+
V1PodSecurityContext,
11+
V1ResourceRequirements,
12+
V1Service,
13+
V1ServicePort,
14+
V1ServiceSpec,
15+
)
16+
from pydantic import PrivateAttr
17+
18+
from src.deployments.core.builders import StatefulSetBuilder
19+
20+
# Project Imports
21+
from src.deployments.core.configs.container import ContainerConfig, Image
22+
from src.deployments.core.configs.helpers.identity import apply_identity
23+
from src.deployments.core.configs.helpers.utils import find_container_config, get_config
24+
from src.deployments.core.configs.pod import PodSpecConfig
25+
26+
27+
class NodesBuilder(StatefulSetBuilder):
28+
_service_name: str = PrivateAttr(default="core-nodes-internal")
29+
_service_account_name: str = PrivateAttr(default="secret-creator")
30+
_container_name: str = PrivateAttr(default="logos-core-container")
31+
_name: str = PrivateAttr(default="logoscore")
32+
_namespace: Optional[str] = PrivateAttr(default=None)
33+
_image: Image = PrivateAttr(
34+
default_factory=lambda: Image(repo="pearsonwhite/dst-lc-node", tag="wip3-amd")
35+
)
36+
_enrs: List[str] = PrivateAttr(default_factory=list)
37+
_dns_configs = PrivateAttr(default_factory=list)
38+
_app: str = PrivateAttr(default="zerotenkay-core")
39+
_debug: bool = PrivateAttr(default=False)
40+
41+
def with_container_name(self, container_name: str) -> Self:
42+
self._ensure_container()
43+
container_config = find_container_config(self.config, self._container_name)
44+
self._container_name = container_name
45+
container_config.name = self._container_name
46+
return self
47+
48+
def with_service_name(self, service_name: str) -> Self:
49+
self._service_name = service_name
50+
self._reconcile()
51+
return self
52+
53+
def with_service_account_name(self, service_account_name: str) -> Self:
54+
self._service_account_name = service_account_name
55+
self._reconcile()
56+
return self
57+
58+
def with_dns_service(self, searches) -> Self:
59+
self._dns_configs.extend(searches)
60+
self._reconcile()
61+
return self
62+
63+
def with_config(self, namespace: str, name: Optional[str] = None) -> Self:
64+
if name is not None:
65+
self._name = name
66+
self._namespace = namespace
67+
self._reconcile()
68+
return self
69+
70+
def with_app(self, app: str) -> Self:
71+
self._app = app
72+
self._reconcile()
73+
return self
74+
75+
def with_enrs(
76+
self,
77+
enrs: List[str],
78+
) -> Self:
79+
self._enrs.extend(enrs)
80+
self._ensure_container()
81+
self._reconcile()
82+
return self
83+
84+
def build_dependencies(self) -> dict:
85+
service = V1Service(
86+
api_version="v1",
87+
kind="Service",
88+
metadata=V1ObjectMeta(
89+
name=self._service_name,
90+
namespace=self._namespace,
91+
),
92+
spec=V1ServiceSpec(
93+
cluster_ip="None",
94+
selector={"app": self._app},
95+
ports=[V1ServicePort(port=8645, name="main", target_port=8645)],
96+
),
97+
)
98+
return {"services": [service]}
99+
100+
def with_debug(self, is_debug: bool = True) -> Self:
101+
self._debug = is_debug
102+
self._reconcile()
103+
return self
104+
105+
def _reconcile(self):
106+
self.config.stateful_set_spec.with_service_name(self._service_name, overwrite=True)
107+
self.config.stateful_set_spec.pod_template_spec_config.pod_spec_config.with_service_account_name(
108+
self._service_account_name, overwrite=True
109+
)
110+
self.config.stateful_set_spec.pod_template_spec_config.pod_spec_config.dns_config = None
111+
for dns in self._dns_configs:
112+
search = f"{dns}.{self._namespace}.svc.cluster.local"
113+
self.config.stateful_set_spec.pod_template_spec_config.pod_spec_config.with_dns_search(
114+
search, overwrite=True
115+
)
116+
117+
if self._debug:
118+
self.config.stateful_set_spec.pod_template_spec_config.pod_spec_config.with_security_context(
119+
V1PodSecurityContext(run_as_user=0, fs_group=0), overwrite=True
120+
)
121+
122+
apply_identity(self.config, self._name, self._namespace, self._app)
123+
self._ensure_container()
124+
container_config = find_container_config(self.config, self._container_name)
125+
apply_container_config(container_config, self._container_name, self._image, self._enrs)
126+
127+
def _ensure_container(self):
128+
container_config = find_container_config(self.config, self._container_name, default=None)
129+
if not container_config:
130+
pod_config = get_config(self.config, PodSpecConfig)
131+
pod_config.add_container(
132+
ContainerConfig(name=self._container_name, image_pull_policy="IfNotPresent")
133+
)
134+
135+
def with_image(self, image: Image) -> Self:
136+
self._image = image
137+
self.with_image_in_container(
138+
image=self._image, container_name=self._container_name, overwrite=True
139+
)
140+
return self
141+
142+
143+
def apply_container_config(
144+
config: ContainerConfig, container_name: str, image: Image, enrs: List[str]
145+
) -> ContainerConfig:
146+
config.name = container_name
147+
config.with_image(image, overwrite=True)
148+
config.with_port(V1ContainerPort(container_port=8645), overwrite=True)
149+
config.with_port(V1ContainerPort(container_port=8008), overwrite=True)
150+
config.with_port(V1ContainerPort(container_port=8080), overwrite=True)
151+
config.with_resources(default_resources(), overwrite=True)
152+
153+
# TODO: create readiness probe
154+
# config.with_readiness_probe()
155+
156+
for index, enr in enumerate(enrs):
157+
config.with_env_var(
158+
V1EnvVar(
159+
name=f"ENR{index}",
160+
value=enr,
161+
),
162+
overwrite=True,
163+
)
164+
165+
config.with_env_var(
166+
V1EnvVar(
167+
name="POD_NAME",
168+
value_from=V1EnvVarSource(field_ref=V1ObjectFieldSelector(field_path="metadata.name")),
169+
),
170+
overwrite=True,
171+
)
172+
config.with_env_var(
173+
V1EnvVar(
174+
name="POD_UID",
175+
value_from=V1EnvVarSource(field_ref=V1ObjectFieldSelector(field_path="metadata.uid")),
176+
),
177+
overwrite=True,
178+
)
179+
180+
return config
181+
182+
183+
def default_resources() -> V1ResourceRequirements:
184+
return V1ResourceRequirements(
185+
requests={"memory": "1Gi", "cpu": "500m"},
186+
limits={"memory": "4Gi", "cpu": "2000m"},
187+
)

0 commit comments

Comments
 (0)