Skip to content

Commit 9d3f9a8

Browse files
committed
feat: improved resources API
1 parent 8b8848f commit 9d3f9a8

File tree

7 files changed

+387
-93
lines changed

7 files changed

+387
-93
lines changed

transpire/resources/__init__.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,5 +3,6 @@
33
from .ingress import Ingress
44
from .secret import Secret
55
from .service import Service
6+
from .statefulset import StatefulSet
67

78
__all__ = ["Deployment", "Ingress", "Service", "Secret", "ConfigMap"]

transpire/resources/base.py

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,9 @@ class Resource(Generic[T]):
1212
def __init__(self):
1313
self.patches = []
1414

15+
def name(self) -> str:
16+
return self.obj.metadata.name
17+
1518
def patch(self, *fns: Callable[[dict], dict]) -> Self:
1619
self.patches.extend(fns)
1720
return self

transpire/resources/configmap.py

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
from pathlib import Path
12
from kubernetes import client
23

34
from transpire.resources.base import Resource
@@ -19,3 +20,10 @@ def __init__(
1920
data=data,
2021
)
2122
super().__init__()
23+
24+
@staticmethod
25+
def from_files(name, files: list[Path]):
26+
data = {}
27+
for file in files:
28+
data[file.name] = file.read_text()
29+
return ConfigMap(name=name, data=data)

transpire/resources/deployment.py

Lines changed: 8 additions & 93 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
1-
from typing import List, Self, Union
1+
from typing import Any, List, Union
22

33
from kubernetes import client
44

55
from transpire.resources.base import Resource
6+
from transpire.resources.podspec import PodSpec
67

78

89
class Deployment(Resource[client.V1Deployment]):
@@ -45,98 +46,12 @@ def __init__(
4546
),
4647
)
4748
super().__init__()
48-
49-
def _init_env(self, container_id: int) -> client.V1Container:
50-
container = self.obj.spec.template.spec.containers[container_id]
51-
52-
if container.env_from is None:
53-
container.env_from = []
54-
if container.env is None:
55-
container.env = []
56-
57-
return container
58-
59-
def with_configmap_env(
60-
self, name: str, *, mapping: dict[str, str] | None = None, container_id: int = 0
61-
) -> Self:
62-
container = self._init_env(container_id)
63-
if mapping is None:
64-
container.env_from.append(
65-
client.V1EnvFromSource(
66-
config_map_ref=client.V1ConfigMapEnvSource(
67-
name=name,
68-
)
69-
)
70-
)
71-
else:
72-
container.env.extend(
73-
client.V1EnvVar(
74-
name=envvar_name,
75-
value_from=client.V1EnvVarSource(
76-
config_map_key_ref=client.V1ConfigMapKeySelector(
77-
name=name,
78-
key=cm_key,
79-
)
80-
),
81-
)
82-
for envvar_name, cm_key in mapping.items()
83-
)
84-
return self
85-
86-
def with_secrets_env(
87-
self, name: str, *, mapping: dict[str, str] | None = None, container_id: int = 0
88-
) -> Self:
89-
container = self._init_env(container_id)
90-
if mapping is None:
91-
container.env_from.append(
92-
client.V1EnvFromSource(
93-
secret_ref=client.V1SecretEnvSource(
94-
name=name,
95-
)
96-
)
97-
)
98-
else:
99-
container.env.extend(
100-
client.V1EnvVar(
101-
name=envvar_name,
102-
value_from=client.V1EnvVarSource(
103-
secret_key_ref=client.V1SecretKeySelector(
104-
name=name,
105-
key=secret_key,
106-
)
107-
),
108-
)
109-
for envvar_name, secret_key in mapping.items()
110-
)
111-
return self
112-
113-
def get_container(
114-
self, name: str | None = None, *, remove: bool = False
115-
) -> client.V1Container:
116-
container_list = self.obj.spec.template.spec.containers
117-
118-
if name is None:
119-
if len(container_list) != 1:
120-
raise ValueError("If multiple containers, must pass name.")
121-
return container_list[0]
122-
123-
for i, container in enumerate(container_list):
124-
if container.name == name:
125-
if remove:
126-
return container_list.pop(i)
127-
return container
128-
129-
raise ValueError(f"No such container: {name}")
130-
131-
def add_container(self, container: client.V1Container) -> int:
132-
container_list = self.obj.spec.template.spec.containers
133-
134-
names = set(c.name for c in container_list)
135-
if container.name in names:
136-
raise ValueError(f"Can't use name {container.name}, already in use.")
137-
138-
container_list.append(container)
139-
return len(container_list) - 1
49+
50+
def pod_spec(self) -> PodSpec:
51+
return PodSpec(self.obj.spec.template.spec)
14052

14153
def get_selector(self) -> dict[str, str]:
14254
return {self.SELECTOR_LABEL: self.obj.metadata.name}
55+
56+
def __getattr__(self, name: str) -> Any:
57+
return getattr(self.pod_spec(), name)

0 commit comments

Comments
 (0)