Skip to content

Commit

Permalink
Adds command line script for deploying Open Vault resources (#12)
Browse files Browse the repository at this point in the history
* Adds command line script for deploying Open Vault resources

* Adds ./deploy executable script for parsing command line args.
  (run ./deploy -h for usage).
* Adds module 'deployer' which takes parsed command line args and provides methods
  for various deployment operations.
* Adds Dockerfile and nginx config file for building/deploying the ov-nginx container used for
  serving both ov_wag and ov-frontend web apps.
* Adds __pycache__ to .gitignore.

Closes #11.

* Format with black

* Splits URLs to constants

* Move arg parsing to cli.py, only run deploy steps when run as __main__

* Migrate to pydantic types

* Adds missing deploy_ov_nginx def

* Adds docstrings

* Adds short args -b: backend, -f: frontend, -p: proxy

* Raises Exception if no deployment specified. Removes else clause.

* Migrates from os to subprocess to catch all errors

Co-authored-by: Harpo <ryan_harbert@wgbh.org>
  • Loading branch information
afred and mrharpo authored Jul 8, 2022
1 parent b1aece1 commit 6f4d9f2
Show file tree
Hide file tree
Showing 6 changed files with 221 additions and 0 deletions.
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
# Python
__pycache__

# Database
db/

Expand Down
67 changes: 67 additions & 0 deletions cli.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
from argparse import ArgumentParser


def cli():
"""parse CLI args"""
parser = ArgumentParser(description='Manage Open Vault deployments')
parser.add_argument(
'-c',
'--context',
required=True,
type=str,
choices=['openvault', 'openvault-demo'],
# TODO: elaborate. This is important and a bit complex.
# It requires that your local ~/.kube/config have these two
# contexts present and properly configured.
help='the kubectl context to use in the deployment',
)

parser.add_argument(
'-b',
'--ov_wag',
type=str,
metavar='TAG|COMMIT|BRANCH|HEAD',
help='version of the ov_wag headless CMS backend to be deployed',
)

parser.add_argument(
'-f',
'--ov-frontend',
type=str,
metavar='TAG|COMMIT|BRANCH|HEAD',
help='version of the ov-frontend website to be deployed',
)

parser.add_argument(
'-p',
'--ov-nginx',
action='store_true',
help='rebuild and redeploy ov-nginx image',
)

parser.add_argument(
'--ov_wag-env',
type=str,
metavar='PATH',
default='./ov_wag/env.yml',
help='path to environment file for ov_wag',
)

parser.add_argument(
'--ov_wag-secrets',
type=str,
metavar='PATH',
default='./ov_wag/secrets.yml',
help='path to secrets file for ov_wag',
)

parser.add_argument(
'--ov-frontend-env',
type=str,
metavar='PATH',
default='./ov-frontend/env.yml',
help='path to environment file for ov-frontend',
)

# Parses the command line args.
return parser.parse_args()
17 changes: 17 additions & 0 deletions deploy
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
#!/usr/bin/env python3
###
# Command line tool for managing Open Vault deployments
###
from deployer import Deployer


if __name__ == '__main__':
from cli import cli

args = cli()

# Create a new Deployer instance form parsed command line args.
deployer = Deployer(**vars(args))

# Run the deployment.
deployer.deploy()
119 changes: 119 additions & 0 deletions deployer.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,119 @@
from subprocess import run
from pydantic import BaseModel

OV_WAG_URL = 'https://github.com/WGBH-MLA/ov_wag.git'
OV_FRONTEND_URL = 'https://github.com/WGBH-MLA/ov-frontend.git'


class Deployer(BaseModel):
"""Deployer class
Used for openvault deployment configuration
"""

context: str
ov_wag: str = None
ov_wag_env: str = None
ov_wag_secrets: str = None
ov_frontend: str = None
ov_frontend_env: str = None
ov_nginx: bool = None

def run(self, cmd):
run(cmd, shell=True, check=True)

def __init__(self, **kwargs):
super().__init__(**kwargs)
self.set_current_context()

def set_current_context(self):
"""Switch to the specified kubectl context."""
self.run(f'kubectl config use-context {self.context}')

def build_ov_wag(self):
"""Build the backend ov_wag docker image"""
self.run(f'docker build {OV_WAG_URL}#{self.ov_wag} -t {self.ov_wag_tag}')

def build_ov_frontend(self):
"""Build the frontend ov-frontend docker image"""
self.run(
f'docker build {OV_FRONTEND_URL}#{self.ov_frontend} -t {self.ov_frontend_tag}'
)

def build_nginx(self):
"""Build the proxy nginx docker image"""
self.run(f'docker build ov-nginx')

def push_ov_wag(self):
"""Push the backend ov_wag docker image to hub.docker.com
Requires the user to be logged in"""
self.run(f'docker push {self.ov_wag_tag}')

def push_ov_frontend(self):
"""Push the frontend ov-frontend docker image to hub.docker.com
Requires the user to be logged in"""
self.run(f'docker push {self.ov_frontend_tag}')

def push_nginx(self):
"""Push the proxy nginx docker image to hub.docker.com
Requires the user to be logged in"""
self.run(f'docker push {self.ov_nginx_tag}')

def update_ov_wag_workload(self):
"""Sets the backend pod image to"""
self.run(f'kubectl set image deployment.apps/ov ov={self.ov_wag_tag}')

def update_ov_frontend_workload(self):
self.run(
f'kubectl set image deployment.apps/ov-frontend ov-frontend={self.ov_frontend_tag}'
)

def deploy_ov_wag(self):
"""Deploy the backend"""
print(f'Deploying ov_wag: "{self.ov_wag}"')
self.build_ov_wag()
self.push_ov_wag()
self.update_ov_wag_workload()

def deploy_ov_frontend(self):
"""Deploy the frontend"""
print(f'Deploying ov-frontend: "{self.ov_frontend}"')
self.build_ov_frontend()
self.push_ov_frontend()
self.update_ov_frontend_workload()

def deploy_ov_nginx(self):
"""Deploy the proxy
TODO: deploy proxy"""
print(f'Deploying ov_nginx: "{self.ov_nginx}"')

def deploy(self):
"""Run the deployment process using the current context"""
print(f'Starting deployment using context "{self.context}"')

if not any([self.ov_wag, self.ov_frontend, self.ov_nginx]):
raise Exception(f'Nothing specified for deployment.')
if self.ov_wag:
self.deploy_ov_wag()
if self.ov_frontend:
self.deploy_ov_frontend()
if self.ov_nginx:
self.deploy_ov_nginx()

print('Done!')

@property
def ov_wag_tag(self):
return f'wgbhmla/ov_wag:{self.ov_wag}'

@property
def ov_frontend_tag(self):
return f'wgbhmla/ov-frontend:{self.ov_frontend}'

@property
def ov_nginx_tag(self):
return f'wgbhmla/ov-nginx:latest'
3 changes: 3 additions & 0 deletions ov-nginx/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
FROM foggbh/ov-nginx:latest

COPY ./nginx.conf /etc/nginx/nginx.conf
12 changes: 12 additions & 0 deletions ov-nginx/nginx.conf
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
events {
worker_connections 4096; ## Default: 1024
}

http {
server {
listen 80 default_server;
location / {
proxy_pass http://ov-frontend:3000;
}
}
}

0 comments on commit 6f4d9f2

Please sign in to comment.