6
0
mirror of https://github.com/ChristianLight/tutor.git synced 2024-09-28 20:29:02 +00:00
tutor/configure
Régis Behmo 90247bc409 Move config.json to its (hopefully) final location
It didn't make much sense to store config.json inside the "openedx"
subfolder anymore, since the configuration values now affect all
services.
2018-06-08 17:39:34 -04:00

228 lines
7.2 KiB
Python
Executable File

#! /usr/bin/env python
# coding: utf8
from __future__ import unicode_literals, print_function
import argparse
import codecs
import json
import os
import random
import string
import sys
class Configurator(object):
def __init__(self, silent=False, **default_overrides):
self.__values = []
self.__default_overrides = default_overrides
if silent:
self.__input = None
else:
try:
self.__input = raw_input
except NameError:
self.__input = input
def as_dict(self):
return dict(self.__values)
def add(self, name, question="", default=""):
default = self.__default_overrides.get(name, default)
value = default
if question:
message = question + " (default: \"{}\"): ".format(default)
value = self.ask(message, default)
self.set(name, value)
return self
def add_boolean(self, name, question, default=True):
default = self.__default_overrides.get(name, default)
message = question + " ({}) ".format("Y/n" if default else "y/N")
value = None
while value is None:
answer = self.ask(message, default)
value = {
"y": True,
"n": False,
default: default,
}.get(answer)
self.set(name, value)
return self
def ask(self, message, default):
if self.__input:
return self.__input(message) or default
return default
def get(self, name):
for key, value in self.__values:
if key == name:
return value
return None
def set(self, name, value):
self.__values.append((name, value))
def substitute(src, dst, delimiter='$', **values):
Template = template_class(delimiter)
with codecs.open(src, encoding='utf-8') as fi:
template = Template(fi.read())
try:
substituted = template.substitute(**values)
except KeyError as e:
sys.stderr.write("ERROR Missing config value '{}' for template {}\n".format(e.args[0], src))
sys.exit(1)
with open(dst, 'w') as fo:
fo.write(substituted)
print("Generated config file {} (from template {})".format(dst, src))
def template_class(user_delimiter='$'):
"""
The default delimiter of the python Template class is '$'. Here, we
generate a Template class with a custom delimiter. This cannot be done
after the class creation because the Template metaclass uses the delimiter
value.
"""
class Template(string.Template):
delimiter = user_delimiter
return Template
def main():
# Hack to handle older config.json files that used to be in a different location
# TODO remove me
config_path = os.path.join("config", "config.json")
deprecated_paths = [
"config.json",
os.path.join("config", "openedx", "config.json"),
]
for deprecated_path in deprecated_paths:
if os.path.exists(deprecated_path):
os.rename(deprecated_path, config_path)
parser = argparse.ArgumentParser("Config file generator for Open edX")
parser.add_argument('-c', '--config', default=config_path,
help="Load default values from this file. Config values will be saved there.")
parser.add_argument('-s', '--silent', action='store_true',
help=(
"Be silent and accept all default values. "
"This is good for debugging, but probably not what you want"
))
args = parser.parse_args()
# Load defaults
defaults = {}
if os.path.exists(args.config):
with open(args.config) as f:
defaults = json.load(f)
configurator = Configurator(silent=args.silent, **defaults).add(
'LMS_HOST', "Your website domain name for students (LMS).", 'www.myopenedx.com'
).add(
'CMS_HOST', "Your website domain name for teachers (CMS).", 'studio.myopenedx.com'
).add(
'PLATFORM_NAME', "Platform name/title", "My Open edX"
).add(
'SECRET_KEY', "", random_string(24)
).add(
'MYSQL_DATABASE', "", 'openedx'
).add(
'MYSQL_USERNAME', "", 'openedx'
).add(
'MYSQL_PASSWORD', "", random_string(8),
).add(
'MONGODB_DATABASE', "", 'openedx'
).add(
'XQUEUE_AUTH_USERNAME', "", 'lms'
).add(
'XQUEUE_AUTH_PASSWORD', "", random_string(8),
).add(
'XQUEUE_MYSQL_DATABASE', "", 'xqueue',
).add(
'XQUEUE_MYSQL_USERNAME', "", 'xqueue',
).add(
'XQUEUE_MYSQL_PASSWORD', "", random_string(8),
).add(
'XQUEUE_SECRET_KEY', "", random_string(24),
)
# Save values
with open(args.config, 'w') as f:
json.dump(configurator.as_dict(), f, sort_keys=True, indent=4)
print("\nConfiguration values were saved to ", args.config)
# Open edX
substitute(
os.path.join('config', 'openedx', 'templates', 'lms.env.json.templ'),
os.path.join('config', 'openedx', 'lms.env.json'),
**configurator.as_dict()
)
substitute(
os.path.join('config', 'openedx', 'templates', 'cms.env.json.templ'),
os.path.join('config', 'openedx', 'cms.env.json'),
**configurator.as_dict()
)
substitute(
os.path.join('config', 'openedx', 'templates', 'lms.auth.json.templ'),
os.path.join('config', 'openedx', 'lms.auth.json'),
**configurator.as_dict()
)
substitute(
os.path.join('config', 'openedx', 'templates', 'cms.auth.json.templ'),
os.path.join('config', 'openedx', 'cms.auth.json'),
**configurator.as_dict()
)
substitute(
os.path.join('config', 'openedx', 'templates', 'provision.sh.templ'),
os.path.join('config', 'openedx', 'provision.sh'),
**configurator.as_dict()
)
# Xqueue
substitute(
os.path.join('config', 'xqueue', 'templates', 'universal.py.templ'),
os.path.join('config', 'xqueue', 'universal.py'),
**configurator.as_dict()
)
# MySQL
substitute(
os.path.join('config', 'mysql', 'templates', 'auth.env.templ'),
os.path.join('config', 'mysql', 'auth.env'),
**configurator.as_dict()
)
# Nginx
# We need a different delimiter in nginx config files, because the '$' sign
# is widely used there
substitute(
os.path.join('config', 'nginx', 'templates', 'lms.conf.templ'),
os.path.join('config', 'nginx', 'lms.conf'),
delimiter='£', **configurator.as_dict()
)
substitute(
os.path.join('config', 'nginx', 'templates', 'cms.conf.templ'),
os.path.join('config', 'nginx', 'cms.conf'),
delimiter='£', **configurator.as_dict()
)
# Android
substitute(
os.path.join('config', 'android', 'templates', 'universal.yaml.templ'),
os.path.join('config', 'android', 'universal.yaml'),
**configurator.as_dict()
)
print("\nConfiguration files were successfuly generated. You may now run the app containers.")
def random_string(length):
return "".join([random.choice(string.ascii_letters + string.digits) for _ in range(length)])
if __name__ == '__main__':
main()