Skip to content

Commit

Permalink
Merge pull request #15 from CMIPT/fix-deploy-kaiser
Browse files Browse the repository at this point in the history
Substitute the Sys V init with systemd.
  • Loading branch information
Quentin9922 authored Jul 31, 2024
2 parents a208094 + 4b9f677 commit d6df86c
Show file tree
Hide file tree
Showing 6 changed files with 165 additions and 39 deletions.
22 changes: 22 additions & 0 deletions clean_ubuntu.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/usr/bin/env bash
# USAGE: bash clean_ubuntu.sh [config_file]

config_file=${1:-"config.json"}

# TODO: reuse the log_error and log_info functions from deploy_ubuntu.sh
log_error () {
echo -e "\e[31m[ERROR]: $1\e[0m"
exit 1
}

log_info () {
echo "[INFO]: $1"
}

log_info "Cleaning up..."
python script/deploy_helper.py \
--config-path "$config_file" \
--clean \
--distro ubuntu \
--default-config-path ./config_default.json || \
log_error "Failed to run deploy_helper.py for cleaning up the environment"
3 changes: 0 additions & 3 deletions config.json
Original file line number Diff line number Diff line change
@@ -1,5 +1,2 @@
{
"name": "noname",
"sex": "nosex",
"age": 10
}
5 changes: 0 additions & 5 deletions config_debug.json
Original file line number Diff line number Diff line change
@@ -1,12 +1,7 @@
{
"deploy": true,
"createGitUser": false,
"deployWithDocker": false,
"repositoryDirectory": "~/.local/gcs/repository",
"serviceUser": "gcs",
"servicePassword": "gcs",
"serviceName": "gcs",
"postgresPassword": null,
"debug": true,
"runTest": true
}
30 changes: 30 additions & 0 deletions config_default.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
{
"deploy": true,
"debug": false,
"runTest": false,
"createGitUser": true,
"deployWithDocker": true,
"repositoryDirectory": "/home/git/repositories",
"postgresPassword": null,
"serviceEnable": true,
"serviceName": "gcs",
"serviceSuffix": "service",
"serviceDescription": "Git server center back-end service",
"servicePIDFile": "/var/run/gcs.pid",
"serviceUser": "gcs",
"serviceUserPassword": null,
"serviceWorkingDirectory": "/opt/gcs",
"serviceRestartPolicy": "always",
"serviceRestartDelaySecond": 5,
"serviceStartJavaCommand": "/usr/bin/java",
"serviceStartJavaArgs": [
"-jar"
],
"serviceStartJarFile": "/opt/gcs/gcs.jar",
"serviceAfter": [
"network.target"
],
"serviceWantedBy": [
"multi-user.target"
]
}
11 changes: 9 additions & 2 deletions deploy_ubuntu.sh
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,13 @@ fi
if ! command -v mvn; then
install_package maven
fi
if ! command -v systemctl; then
install_package systemd
fi

python script/deploy_helper.py -f "$config_file" -d ubuntu || \
log_error "Failed to run deploy_helper.py $config_file"
log_info "Deploying..."
python script/deploy_helper.py \
--config-path "$config_file" \
--distro ubuntu \
--default-config-path ./config_default.json || \
log_error "Failed to run deploy_helper.py for deploying the environment"
133 changes: 104 additions & 29 deletions script/deploy_helper.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,14 +12,61 @@
import subprocess


def load_json_file_as_obj(file_path: str):
# open config_path and default_config_path
# union the result as an new obj
# return the new obj or None if error
def load_config_file_as_obj(config_path: str, default_config_path: str):
try:
with open(file_path, 'r', encoding='utf-8') as file:
data = json.load(file, object_hook=lambda d: SimpleNamespace(**d))
with open(config_path, 'r') as f:
config = json.load(f, object_hook=lambda d: SimpleNamespace(**d))
with open(default_config_path, 'r') as f:
default_config = json.load(f, object_hook=lambda d: SimpleNamespace(**d))
except Exception as e:
print(f"Error: {e}")
return None
return data
for key in default_config.__dict__:
if not hasattr(config, key):
setattr(config, key, getattr(default_config, key))
return config


def parse_iterable_into_str(iterable, sep=" "):
res = ""
for it in iterable:
res += f'{it}{sep}'
res.strip()
return res


def create_systemd_service(config):
if config == None:
return -1
exec_start = parse_iterable_into_str(
[config.serviceStartJavaCommand] + config.serviceStartJavaArgs + [config.serviceStartJarFile])
wanted_by = parse_iterable_into_str(config.serviceWantedBy)
after = parse_iterable_into_str(config.serviceAfter)
service_full_path = f'/etc/systemd/system/{config.serviceName}.{config.serviceSuffix}'
gcs_file_content = \
f"""\
[Unit]
Description={config.serviceDescription}
After={after}
[Service]
PIDFile={config.servicePIDFile}
User={config.serviceUser}
WorkingDirectory={config.serviceWorkingDirectory}
Restart={config.serviceRestartPolicy}
RestartSec={config.serviceRestartDelaySecond}
ExecStart={exec_start}
[Install]
WantedBy={wanted_by}
"""
res = os.system(
f'echo "{gcs_file_content}" | sudo tee {service_full_path}')
if res != 0:
exit(res)


# TODO: add checker to check
Expand All @@ -32,13 +79,7 @@ def deploy_on_ubuntu(config):
print("Test failed.")
return res
if config.deploy:
if os.path.exists(f'/etc/init.d/{config.serviceName}'):
res = os.system(f'sudo service {config.serviceName} stop && '
f'sudo rm /etc/init.d/{config.serviceName} && '
f'sudo systemctl daemon-reload')
if res != 0:
return res
res = subprocess.run('script/get_jar_position.sh', shell=True,
res = subprocess.run('bash script/get_jar_position.sh', shell=True,
capture_output=True, text=True)
if res.returncode != 0:
return res.returncode
Expand All @@ -49,34 +90,68 @@ def deploy_on_ubuntu(config):

if os.system(f"cat /etc/passwd | grep -w -E '^{config.serviceUser}'") != 0:
os.system(f'sudo useradd {config.serviceUser}')
process = subprocess.Popen(['sudo', 'chpasswd'], stdin=subprocess.PIPE,
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True)
assert(process.stdin is not None)
process.stdin.write(f'{config.serviceUser}:{config.servicePassword}')
process.stdin.flush()
process.communicate()

res = os.system(
f'sudo chown {config.serviceUser}:{config.serviceUser} {package_path}')
if res != 0:
return res
res = os.system(f'sudo ln -s {package_path} /etc/init.d/{config.serviceName}')
if config.serviceUserPassword == None or config.serviceUserPassword == "":
os.system(f'sudo passwd -d {config.serviceUser}')
else:
process = subprocess.Popen(['sudo', 'chpasswd'], stdin=subprocess.PIPE,
stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=True)
assert(process.stdin is not None)
process.stdin.write(f'{config.serviceUser}:{config.serviceUserPassword}')
process.stdin.flush()
process.communicate()

if not os.path.exists(os.path.dirname(config.serviceStartJarFile)):
os.system(f'sudo mkdir -p {os.path.dirname(config.serviceStartJarFile)}')
res = os.system(f'sudo cp {package_path} {config.serviceStartJarFile}')
if res != 0:
return res
res = os.system(
f'sudo systemctl daemon-reload && sudo service {config.serviceName} start &')
create_systemd_service(config)
if config.serviceEnable:
res = os.system(f'sudo systemctl enable {config.serviceName}')
if res != 0:
return res
else:
res = os.system(f'sudo systemctl disable {config.serviceName}')
if res != 0:
return res
res = os.system(f'sudo systemctl start {config.serviceName}')
if res != 0:
return res
# TODO: finish deploy on docker


# TODO: add checker to check
def clean(config):
os.system(f'sudo systemctl disable {config.serviceName}')
os.system(f'sudo systemctl stop {config.serviceName}')
if os.path.exists(f'/etc/systemd/system/{config.serviceName}.{config.serviceSuffix}'):
os.system(
f'sudo rm -rf /etc/systemd/system/{config.serviceName}.{config.serviceSuffix} && '
f'sudo systemctl daemon-reload')
os.system(f'sudo systemctl reset-failed {config.serviceName}')
if os.path.exists(f'{config.serviceWorkingDirectory}'):
os.system(f'sudo rm -rf {config.serviceWorkingDirectory}')
if os.path.exists(f'{config.serviceStartJarFile}'):
os.system(f'sudo rm -rf {config.serviceStartJarFile}')
if os.path.exists(f'{config.servicePIDFile}'):
os.system(f'sudo rm -rf {config.servicePIDFile}')
if os.system(f"cat /etc/passwd | grep -w -E '^{config.serviceUser}'") == 0:
os.system(f'sudo userdel {config.serviceUser}')
os.system(f'mvn clean')


if __name__ == "__main__":
parser = argparse.ArgumentParser(
description="Deploy the project when the environment is ready.")
parser.add_argument('-f', '--file_path', nargs='?', default='../config.json',
parser.add_argument('--config-path', nargs='?', default='../config.json',
type=str, help="Path to the JSON file")
parser.add_argument('-d', '--distro', nargs='?', default='ubuntu',
parser.add_argument('--distro', nargs='?', default='ubuntu',
type=str, help="Linux distribution")
parser.add_argument('--default-config-path', nargs='?', default='../config_default.json',
type=str, help="Linux distribution")
parser.add_argument('--clean', action='store_true', help="Clean up the project")
args = parser.parse_args()
if args.distro == 'ubuntu':
exit(deploy_on_ubuntu(load_json_file_as_obj(args.file_path)))
if args.clean:
clean(load_config_file_as_obj(args.config_path, args.default_config_path))
elif args.distro == 'ubuntu':
exit(deploy_on_ubuntu(load_config_file_as_obj(args.config_path, args.default_config_path)))

0 comments on commit d6df86c

Please sign in to comment.