-
Notifications
You must be signed in to change notification settings - Fork 0
/
docker-setup.py
133 lines (104 loc) · 4.33 KB
/
docker-setup.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
from dotenv import load_dotenv
import re
from string import Template
import logging
import os
# Load the environment variables from the file for build.
# Docker enviroment variables are runtime context by default
load_dotenv(override=True) # take environment variables from .env.
logger = logging.getLogger(__name__)
# Keys needed from .env for substitution
ENV_VARS_NEEDED = {"URL", "USERNAME", "API_TOKEN", "DEVICE_NAME"}
def check_env() -> bool:
"""Check if the .env variables are ready to be substituted into prometheus.yml
Returns:
bool: True if all of the variables are OK. False otherwise
"""
def _is_valid_variable(INPUT_STRING: str) -> bool:
"""Checks that the env variable is valid
Args:
INPUT_STRING (str): The prospective variable
Returns:
bool: True if valid, False otherwise
"""
# https://regex101.com/r/yfRDu6/2
REGEX = r'^[a-zA-Z0-9!@#$%^&*()_+\-=\[\]{};\':"\\|,.<>\/?]+$'
return re.match(pattern=REGEX, string=INPUT_STRING) is not None
something_wrong = False
for env_var_name in ENV_VARS_NEEDED:
env_var_value = os.getenv(env_var_name)
if env_var_value is None:
# Missing variable
logger.error(
f"Missing .env variable: {env_var_name}. Please add it into .env")
something_wrong = True
elif env_var_value == "":
# Blank variable
logger.error(
f"Blank .env variable: {env_var_name}. Please edit .env to define a value")
something_wrong = True
elif (not _is_valid_variable(env_var_value)):
logger.error(
f"Invalid variable contents. Please use alphanumeric values only")
if not something_wrong:
logger.info(
"Note that previous initialisations of .env variables may still be in scope if not re-defined in .env")
logger.info("All environment variables defined.")
return not something_wrong
def substitute_prometheus() -> bool:
PATH_PROMETHEUS = "prometheus.yml"
PATH_PROMETHEUS_TEMPLATE = os.path.join(
"templates", "prometheus.yml.template"
)
# Check template file exists
if not os.path.isfile(PATH_PROMETHEUS_TEMPLATE):
logger.error(f"Template file: {PATH_PROMETHEUS_TEMPLATE} missing")
return False
with open(PATH_PROMETHEUS_TEMPLATE, "r") as r:
TEMPLATE_CONTENT = r.read()
TEMPLATE_PROMETHEUS = Template(TEMPLATE_CONTENT)
# Create mapping to substitute
template_mapping = {}
for env_var_name in ENV_VARS_NEEDED:
env_var_value = os.getenv(env_var_name)
if env_var_value is None or env_var_value == "":
logger.error(
f"Environment variable: {env_var_name} is missing or blank")
return False
template_mapping[env_var_name] = env_var_value
try:
SUBSTITUTED_CONTENT = TEMPLATE_PROMETHEUS.substitute(template_mapping)
except KeyError as E:
logger.error(f"{PATH_PROMETHEUS_TEMPLATE} could not be substituted")
logger.error(f"KeyError: {E}")
return False
if not os.path.isfile(PATH_PROMETHEUS):
logger.info(f"Creating {PATH_PROMETHEUS}")
with open(PATH_PROMETHEUS, "w") as w:
w.write(SUBSTITUTED_CONTENT)
logger.info(
f"Successfully substituted {len(ENV_VARS_NEEDED)} environment variables into {PATH_PROMETHEUS}")
return True
def main() -> None:
# Start logger
# Copy format from speedtest image
# https://github.com/MiguelNdeCarvalho/speedtest-exporter/blob/8e4a39b9c0282102a9868f43b60dc99465dd0974/src/exporter.py#L14
FORMAT_STRING = 'level=%(levelname)s datetime=%(asctime)s %(message)s'
logging.basicConfig(encoding='utf-8',
level=logging.DEBUG,
format=FORMAT_STRING)
logger.info(f'Started {__file__}')
# Check if .env has been created and filled out
if (check_env()):
# Put those values into prometheus.yml
if (substitute_prometheus()):
logger.info("Completed prometheus.yml procedure successfully")
else:
logger.error("Failed prometheus.yml procedure")
exit(1)
else:
logger.info("Skipping prometheus.yml procedure")
exit(1)
logger.info(f'Finished {__file__}')
if __name__ == "__main__":
main()