From 9be848e5e241f385c27f87a3fbc3c9e9d1cbc02e Mon Sep 17 00:00:00 2001 From: Tim Van Baak Date: Thu, 23 Jan 2020 15:13:34 -0800 Subject: [PATCH] Fix namespaces --- amanuensis/__main__.py | 4 +-- amanuensis/cli/__init__.py | 12 +++---- amanuensis/cli/helpers.py | 16 ++++----- amanuensis/cli/lexicon.py | 61 ++++++++++++++++--------------- amanuensis/cli/server.py | 31 ++++++++-------- amanuensis/cli/user.py | 65 ++++++++++++++++++---------------- amanuensis/config/__init__.py | 20 +++++------ amanuensis/config/init.py | 55 ++++++++++++++-------------- amanuensis/config/loader.py | 2 +- amanuensis/lexicon/__init__.py | 20 +++++------ amanuensis/lexicon/manage.py | 40 ++++++++++----------- amanuensis/server/__init__.py | 12 +++---- amanuensis/server/auth.py | 6 ++-- amanuensis/server/home.py | 8 ++--- amanuensis/server/lexicon.py | 14 ++++---- amanuensis/user.py | 34 +++++++++--------- 16 files changed, 203 insertions(+), 197 deletions(-) diff --git a/amanuensis/__main__.py b/amanuensis/__main__.py index 79996bd..c43b07e 100644 --- a/amanuensis/__main__.py +++ b/amanuensis/__main__.py @@ -4,8 +4,8 @@ import os import traceback # Module imports -import cli -import config +import amanuensis.cli as cli +import amanuensis.config as config def repl(args): diff --git a/amanuensis/cli/__init__.py b/amanuensis/cli/__init__.py index 8460fed..de0b932 100644 --- a/amanuensis/cli/__init__.py +++ b/amanuensis/cli/__init__.py @@ -10,8 +10,8 @@ def server_commands(commands={}): if commands: return commands - import cli.server - for name, func in vars(cli.server).items(): + import amanuensis.cli.server + for name, func in vars(amanuensis.cli.server).items(): if name.startswith("command_"): name = name[8:].replace("_", "-") commands[name] = func @@ -19,8 +19,8 @@ def server_commands(commands={}): def lexicon_commands(commands={}): if commands: return commands - import cli.lexicon - for name, func in vars(cli.lexicon).items(): + import amanuensis.cli.lexicon + for name, func in vars(amanuensis.cli.lexicon).items(): if name.startswith("command_"): name = name[8:].replace("_", "-") commands["lexicon-" + name] = func @@ -28,8 +28,8 @@ def lexicon_commands(commands={}): def user_commands(commands={}): if commands: return commands - import cli.user - for name, func in vars(cli.user).items(): + import amanuensis.cli.user + for name, func in vars(amanuensis.cli.user).items(): if name.startswith("command_"): name = name[8:].replace("_", "-") commands["user-" + name] = func diff --git a/amanuensis/cli/helpers.py b/amanuensis/cli/helpers.py index 20196a8..e21feb0 100644 --- a/amanuensis/cli/helpers.py +++ b/amanuensis/cli/helpers.py @@ -43,10 +43,10 @@ def requires_lexicon(command): subp_val = hasattr(cmd_args, "lexicon") and getattr(cmd_args, "lexicon") val = subp_val or base_val or None if not val: - import config - config.logger.error("This command requires specifying a lexicon") + from amanuensis.config import logger + logger.error("This command requires specifying a lexicon") return -1 - from lexicon import LexiconModel + from amanuensis.lexicon import LexiconModel cmd_args.lexicon = val#LexiconModel.by(name=val).name command(cmd_args) augmented_command.__dict__['wrapper'] = True @@ -64,10 +64,10 @@ def requires_username(command): subp_val = hasattr(cmd_args, "username") and getattr(cmd_args, "username") val = subp_val or base_val or None if not val: - import config - config.logger.error("This command requires specifying a user") + from amanuensis.config import logger + logger.error("This command requires specifying a user") return -1 - from user import UserModel + from amanuensis.user import UserModel cmd_args.username = val#UserModel.by(name=val).name command(cmd_args) augmented_command.__dict__['wrapper'] = True @@ -84,7 +84,7 @@ def config_get(cfg, pathspec): path is the full pathspec, unsplit """ import json - from config import logger + from amanuensis.config import logger if pathspec is CONFIG_GET_ROOT_VALUE: path = [] @@ -105,7 +105,7 @@ def config_set(obj_id, cfg, set_tuple): set_tuple is a tuple of the pathspec and the value """ import json - from config import logger + from amanuensis.config import logger pathspec, value = set_tuple if not pathspec: logger.error("Path must be non-empty") diff --git a/amanuensis/cli/lexicon.py b/amanuensis/cli/lexicon.py index 8122ec8..a5e9525 100644 --- a/amanuensis/cli/lexicon.py +++ b/amanuensis/cli/lexicon.py @@ -1,4 +1,4 @@ -from cli.helpers import ( +from amanuensis.cli.helpers import ( add_argument, no_argument, requires_lexicon, requires_username, config_get, config_set, CONFIG_GET_ROOT_VALUE) @@ -17,9 +17,9 @@ def command_create(args): settings are as desired before opening the lexicon for player joins. """ # Module imports - from config import logger - from lexicon.manage import valid_name, create_lexicon - from user import UserModel + from amanuensis.config import logger + from amanuensis.lexicon.manage import valid_name, create_lexicon + from amanuensis.user import UserModel # Verify arguments if not valid_name(args.lexicon): @@ -42,9 +42,9 @@ def command_delete(args): Delete a lexicon and optionally its data """ # Module imports - from config import logger - from lexicon import LexiconModel - from lexicon.manage import delete_lexicon + from amanuensis.config import logger + from amanuensis.lexicon import LexiconModel + from amanuensis.lexicon.manage import delete_lexicon # Verify arguments lex = LexiconModel.by(name=args.lexicon) @@ -63,7 +63,7 @@ def command_list(args): List all lexicons and their statuses """ # Module imports - from lexicon.manage import get_all_lexicons + from amanuensis.lexicon.manage import get_all_lexicons # Internal call lexicons = get_all_lexicons() @@ -91,8 +91,8 @@ def command_config(args): Interact with a lexicon's config """ # Module imports - from config import logger, json_ro, json_rw - from lexicon import LexiconModel + from amanuensis.config import logger, json_ro, json_rw + from amanuensis.lexicon import LexiconModel # Verify arguments if args.get and args.set: @@ -123,10 +123,10 @@ def command_player_add(args): Add a player to a lexicon """ # Module imports - from config import logger - from lexicon import LexiconModel - from lexicon.manage import add_player - from user import UserModel + from amanuensis.config import logger + from amanuensis.lexicon import LexiconModel + from amanuensis.lexicon.manage import add_player + from amanuensis.user import UserModel # Verify arguments u = UserModel.by(name=args.username) @@ -152,10 +152,10 @@ def command_player_remove(args): they control but does not delete any character data. """ # Module imports - from config import logger - from lexicon import LexiconModel - from lexicon.manage import remove_player - from user import UserModel + from amanuensis.config import logger + from amanuensis.lexicon import LexiconModel + from amanuensis.lexicon.manage import remove_player + from amanuensis.user import UserModel # Verify arguments u = UserModel.by(name=args.username) @@ -181,8 +181,8 @@ def command_player_list(args): """ import json # Module imports - from lexicon import LexiconModel - from user import UserModel + from amanuensis.lexicon import LexiconModel + from amanuensis.user import UserModel # Verify arguments lex = LexiconModel.by(name=args.lexicon) @@ -209,10 +209,10 @@ def command_char_create(args): The specified player will be set as the character's player. """ # Module imports - from config import logger - from lexicon import LexiconModel - from lexicon.manage import add_character - from user import UserModel + from amanuensis.config import logger + from amanuensis.lexicon import LexiconModel + from amanuensis.lexicon.manage import add_character + from amanuensis.user import UserModel # Verify arguments u = UserModel.by(name=args.username) @@ -223,7 +223,7 @@ def command_char_create(args): if lex is None: logger.error("Could not find lexicon '{}'".format(args.lexicon)) return -1 - # u in lx + # u in lx TODO # Internal call add_character(lex, u, {"name": args.charname}) @@ -239,9 +239,9 @@ def command_char_delete(args): they have contributed rather than deleting it. """ # Module imports - from config import logger - from lexicon import LexiconModel - from lexicon.manage import delete_character + from amanuensis.config import logger + from amanuensis.lexicon import LexiconModel + from amanuensis.lexicon.manage import delete_character # Verify arguments lex = LexiconModel.by(name=args.lexicon) @@ -259,7 +259,7 @@ def command_char_list(args): """ import json # Module imports - from lexicon import LexiconModel + from amanuensis.lexicon import LexiconModel # Verify arguments lex = LexiconModel.by(name=args.lexicon) @@ -291,4 +291,7 @@ def command_publish_turn(args): The --force flag bypasses the publish.quorum and publish.block_on_ready settings. """ + # Module imports + from amanuensis.config import logger + raise NotImplementedError() # TODO \ No newline at end of file diff --git a/amanuensis/cli/server.py b/amanuensis/cli/server.py index 9aa1a2e..69c4c52 100644 --- a/amanuensis/cli/server.py +++ b/amanuensis/cli/server.py @@ -1,6 +1,6 @@ import os -from cli.helpers import ( +from amanuensis.cli.helpers import ( add_argument, no_argument, config_get, config_set, CONFIG_GET_ROOT_VALUE) @@ -20,7 +20,7 @@ def command_init(args): from the indexes will be deleted, and stale index entries will be removed. """ # Module imports - from config.init import create_config_dir + from amanuensis.config.init import create_config_dir # Verify arguments if args.refresh and not os.path.isdir(args.config_dir): @@ -39,13 +39,13 @@ def command_generate_secret(args): been generated. """ import os - - import config + # Module imports + from amanuensis.config import json_rw, logger secret_key = os.urandom(32) - with config.json_rw("config.json") as cfg: + with json_rw("config.json") as cfg: cfg['secret_key'] = secret_key.hex() - config.logger.info("Regenerated Flask secret key") + logger.info("Regenerated Flask secret key") @add_argument("-a", "--address", default="127.0.0.1") @@ -57,13 +57,13 @@ def command_run(args): The default Flask server is not secure, and should only be used for development. """ - import server - import config + from amanuensis.server import app + from amanuensis.config import get, logger - if config.get("secret_key") is None: - config.logger.error("Can't run server without a secret_key. Run generate-secret first") + if get("secret_key") is None: + logger.error("Can't run server without a secret_key. Run generate-secret first") return -1 - server.app.run(host=args.address, port=args.port) + app.run(host=args.address, port=args.port) @add_argument("--get", metavar="PATHSPEC", dest="get", @@ -78,16 +78,17 @@ def command_config(args): a dot-separated sequence of keys. """ import json - import config + # Module imports + from amanuensis.config import json_ro, json_rw, logger if args.get and args.set: - config.logger.error("Specify one of --get and --set") + logger.error("Specify one of --get and --set") return -1 if args.get: - with config.json_ro('config.json') as cfg: + with json_ro('config.json') as cfg: config_get(cfg, args.get) if args.set: - with config.json_rw('config.json') as cfg: + with json_rw('config.json') as cfg: config_set("config", cfg, args.set) diff --git a/amanuensis/cli/user.py b/amanuensis/cli/user.py index f96ecdc..8819876 100644 --- a/amanuensis/cli/user.py +++ b/amanuensis/cli/user.py @@ -1,6 +1,6 @@ import shutil -from cli.helpers import ( +from amanuensis.cli.helpers import ( add_argument, no_argument, requires_username, config_get, config_set, CONFIG_GET_ROOT_VALUE) @@ -12,26 +12,26 @@ def command_create(args): Create a user """ import json - - import user - import config + # Module imports + from amanuensis.config import logger, json_ro + from amanuensis.user import UserModel, valid_username, valid_email, create_user # Verify or query parameters - if not user.valid_username(args.username): - config.logger.error("Invalid username: usernames may only contain alphanumeric characters, dashes, and underscores") + if not valid_username(args.username): + logger.error("Invalid username: usernames may only contain alphanumeric characters, dashes, and underscores") return -1 - if user.UserModel.by(name=args.username) is not None: - config.logger.error("Invalid username: username is already taken") + if UserModel.by(name=args.username) is not None: + logger.error("Invalid username: username is already taken") return -1 if not args.displayname: args.displayname = args.username - if not user.valid_email(args.email): - config.logger.error("Invalid email") + if not valid_email(args.email): + logger.error("Invalid email") return -1 # Create user - new_user, tmp_pw = user.create_user(args.username, args.displayname, args.email) - with config.json_ro(new_user.config_path) as js: + new_user, tmp_pw = create_user(args.username, args.displayname, args.email) + with json_ro(new_user.config_path) as js: print(json.dumps(js, indent=2)) print("Username: {}\nUser ID: {}\nPassword: {}".format(args.username, new_user.uid, tmp_pw)) @@ -41,31 +41,33 @@ def command_delete(args): Delete a user """ import os + # Module imports + from amanuensis.config import logger, prepend - import config - - user_path = config.prepend('user', args.id) + user_path = prepend('user', args.id) if not os.path.isdir(user_path): - config.logger.error("No user with that id") + logger.error("No user with that id") return -1 else: shutil.rmtree(user_path) - with config.json_rw('user', 'index.json') as j: + with json_rw('user', 'index.json') as j: if args.id in j: del j[uid] + # TODO + @no_argument def command_list(args): """List all users""" import os + # Module imports + from amanuensis.config import prepend, json_ro - import config - - user_dirs = os.listdir(config.prepend('user')) + user_dirs = os.listdir(prepend('user')) users = [] for uid in user_dirs: if uid == "index.json": continue - with config.json_ro('user', uid, 'config.json') as user: + with json_ro('user', uid, 'config.json') as user: users.append(user) users.sort(key=lambda u: u['username']) for user in users: @@ -83,24 +85,25 @@ def command_config(args): Interact with a user's config """ import json - import config - from user import UserModel + # Module imports + from amanuensis.config import logger, json_ro, json_rw + from amanuensis.user import UserModel if args.get and args.set: - config.logger.error("Specify one of --get and --set") + logger.error("Specify one of --get and --set") return -1 u = UserModel.by(name=args.username) if not u: - config.logger.error("User not found") + logger.error("User not found") return -1 if args.get: - with config.json_ro('user', u.id, 'config.json') as cfg: + with json_ro('user', u.id, 'config.json') as cfg: config_get(cfg, args.get) if args.set: - with config.json_rw('user', u.id, 'config.json') as cfg: + with json_rw('user', u.id, 'config.json') as cfg: config_set(u.id, cfg, args.set) @add_argument("--username", help="The user to change password for") @@ -110,15 +113,15 @@ def command_passwd(args): """ import getpass import os - - import config - from user import UserModel + # Module imports + from amanuensis.config import logger + from amanuensis.user import UserModel if not args.username: args.username = input("Username: ") u = UserModel.by(name=args.username) if u is None: - config.logger.error("No user with username '{}'".format(args.username)) + logger.error("No user with username '{}'".format(args.username)) return -1 pw = getpass.getpass("Password: ") u.set_password(pw) diff --git a/amanuensis/config/__init__.py b/amanuensis/config/__init__.py index 96e152c..f886393 100644 --- a/amanuensis/config/__init__.py +++ b/amanuensis/config/__init__.py @@ -4,9 +4,9 @@ import logging import os # Module imports -from errors import MissingConfigError, MalformedConfigError -import config.init -import config.loader +from amanuensis.errors import MissingConfigError, MalformedConfigError +import amanuensis.config.init +import amanuensis.config.loader # Environment variable name constants @@ -31,10 +31,10 @@ def init_config(args): """ global CONFIG_DIR, GLOBAL_CONFIG, logger CONFIG_DIR = args.config_dir - config.init.verify_config_dir(CONFIG_DIR) - with config.loader.json_ro(os.path.join(CONFIG_DIR, "config.json")) as cfg: + amanuensis.config.init.verify_config_dir(CONFIG_DIR) + with amanuensis.config.loader.json_ro(os.path.join(CONFIG_DIR, "config.json")) as cfg: GLOBAL_CONFIG = cfg - config.init.init_logging(args, GLOBAL_CONFIG['logging']) + amanuensis.config.init.init_logging(args, GLOBAL_CONFIG['logging']) logger = logging.getLogger("amanuensis") def get(key): @@ -47,13 +47,13 @@ def prepend(*path): return joined def open_sh(*path, mode): - return config.loader.open_sh(prepend(*path), mode) + return amanuensis.config.loader.open_sh(prepend(*path), mode) def open_ex(*path, mode): - return config.loader.open_ex(prepend(*path), mode) + return amanuensis.config.loader.open_ex(prepend(*path), mode) def json_ro(*path): - return config.loader.json_ro(prepend(*path)) + return amanuensis.config.loader.json_ro(prepend(*path)) def json_rw(*path): - return config.loader.json_rw(prepend(*path)) \ No newline at end of file + return amanuensis.config.loader.json_rw(prepend(*path)) \ No newline at end of file diff --git a/amanuensis/config/init.py b/amanuensis/config/init.py index 2d9a8e0..933aecb 100644 --- a/amanuensis/config/init.py +++ b/amanuensis/config/init.py @@ -6,10 +6,10 @@ import os import shutil # Module imports -from errors import MissingConfigError, MalformedConfigError -import config -from config.loader import json_ro -import resources +from amanuensis.errors import MissingConfigError, MalformedConfigError +from amanuensis.config.loader import json_ro, json_rw +from amanuensis.resources import get_stream + def create_config_dir(config_dir, refresh=False): """ @@ -18,23 +18,24 @@ def create_config_dir(config_dir, refresh=False): from collections import OrderedDict import fcntl - path = config.prepend + def prepend(*path): + joined = os.path.join(*path) + if not joined.startswith(config_dir): + joined = os.path.join(config_dir, joined) + return joined # Create the directory if it doesn't exist. if not os.path.isdir(config_dir): os.mkdir(config_dir) - # Initialize the config dir without verification - config.CONFIG_DIR = config_dir - # The directory should be empty if we're not updating an existing one. if len(os.listdir(config_dir)) > 0 and not refresh: print("Directory {} is not empty".format(config_dir)) return -1 # Update or create global config. - def_cfg = resources.get_stream("global.json") - global_config_path = path("config.json") + def_cfg = get_stream("global.json") + global_config_path = prepend("config.json") if refresh and os.path.isfile(global_config_path): # We need to write an entirely different ordereddict to the config # file, so we mimic the config.loader functionality manually. @@ -56,34 +57,34 @@ def create_config_dir(config_dir, refresh=False): cfg_file.truncate() fcntl.lockf(cfg_file, fcntl.LOCK_UN) else: - with open(path("config.json"), 'wb') as f: + with open(prepend("config.json"), 'wb') as f: f.write(def_cfg.read()) # Ensure pidfile exists. - if not os.path.isfile(path("pid")): - with open(path("pid"), 'w') as f: + if not os.path.isfile(prepend("pid")): + with open(prepend("pid"), 'w') as f: f.write(str(os.getpid())) # Ensure lexicon subdir exists. - if not os.path.isdir(path("lexicon")): - os.mkdir(path("lexicon")) - if not os.path.isfile(path("lexicon", "index.json")): - with open(path("lexicon", "index.json"), 'w') as f: + if not os.path.isdir(prepend("lexicon")): + os.mkdir(prepend("lexicon")) + if not os.path.isfile(prepend("lexicon", "index.json")): + with open(prepend("lexicon", "index.json"), 'w') as f: json.dump({}, f) # Ensure user subdir exists. - if not os.path.isdir(path("user")): - os.mkdir(path("user")) - if not os.path.isfile(path('user', 'index.json')): - with open(path('user', 'index.json'), 'w') as f: + if not os.path.isdir(prepend("user")): + os.mkdir(prepend("user")) + if not os.path.isfile(prepend('user', 'index.json')): + with open(prepend('user', 'index.json'), 'w') as f: json.dump({}, f) if refresh: for dir_name in ('lexicon', 'user'): # Clean up unindexed folders - with config.json_ro(dir_name, 'index.json') as index: + with json_ro(prepend(dir_name, 'index.json')) as index: known = list(index.values()) - entries = os.listdir(path(dir_name)) + entries = os.listdir(prepend(dir_name)) for dir_entry in entries: if dir_entry == "index.json": continue @@ -91,12 +92,12 @@ def create_config_dir(config_dir, refresh=False): continue print("Removing unindexed folder: '{}/{}'" .format(dir_name, dir_entry)) - shutil.rmtree(path(dir_name, dir_entry)) + shutil.rmtree(prepend(dir_name, dir_entry)) # Remove orphaned index listings - with config.json_rw(dir_name, 'index.json') as index: + with json_rw(prepend(dir_name, 'index.json')) as index: for name, entry in index.items(): - if not os.path.isdir(path(dir_name, entry)): + if not os.path.isdir(prepend(dir_name, entry)): print("Removing stale {} index entry '{}: {}'" .format(dir_name, name, entry)) del index[name] @@ -115,7 +116,7 @@ def verify_config_dir(config_dir): if not os.path.isfile(global_config_path): raise MissingConfigError("Config directory missing global config file: {}".format(config_dir)) # Check that global config file has all the default settings - def_cfg_s = resources.get_stream("global.json") + def_cfg_s = get_stream("global.json") def_cfg = json.load(def_cfg_s) with json_ro(global_config_path) as global_config_file: for key in def_cfg.keys(): diff --git a/amanuensis/config/loader.py b/amanuensis/config/loader.py index 4cef7d1..87e694a 100644 --- a/amanuensis/config/loader.py +++ b/amanuensis/config/loader.py @@ -5,7 +5,7 @@ import json import os # Module imports -from errors import ReadOnlyError +from amanuensis.errors import ReadOnlyError class AttrOrderedDict(OrderedDict): diff --git a/amanuensis/lexicon/__init__.py b/amanuensis/lexicon/__init__.py index 0f64fd0..5086001 100644 --- a/amanuensis/lexicon/__init__.py +++ b/amanuensis/lexicon/__init__.py @@ -1,8 +1,8 @@ import os import time -from errors import InternalMisuseError, IndexMismatchError, MissingConfigError -import config +from amanuensis.errors import InternalMisuseError, IndexMismatchError, MissingConfigError +from amanuensis.config import prepend, json_ro, json_rw class LexiconModel(): def by(lid=None, name=None): @@ -18,24 +18,24 @@ class LexiconModel(): if not lid and not name: raise ValueError("One of lid or name must be not None") if not lid: - with config.json_ro('lexicon', 'index.json') as index: + with json_ro('lexicon', 'index.json') as index: lid = index.get(name) if not lid: return None - if not os.path.isdir(config.prepend('lexicon', lid)): + if not os.path.isdir(prepend('lexicon', lid)): raise IndexMismatchError("lexicon={} lid={}".format(name, lid)) - if not os.path.isfile(config.prepend('lexicon', lid, 'config.json')): + if not os.path.isfile(prepend('lexicon', lid, 'config.json')): raise MissingConfigError("lid={}".format(lid)) return LexiconModel(lid) def __init__(self, lid): - if not os.path.isdir(config.prepend('lexicon', lid)): + if not os.path.isdir(prepend('lexicon', lid)): raise ValueError("No lexicon with lid {}".format(lid)) - if not os.path.isfile(config.prepend('lexicon', lid, 'config.json')): + if not os.path.isfile(prepend('lexicon', lid, 'config.json')): raise FileNotFoundError("Lexicon {} missing config.json".format(lid)) self.id = str(lid) - self.config_path = config.prepend('lexicon', lid, 'config.json') - with config.json_ro(self.config_path) as j: + self.config_path = prepend('lexicon', lid, 'config.json') + with json_ro(self.config_path) as j: self.config = j def __getattr__(self, key): @@ -45,7 +45,7 @@ class LexiconModel(): def log(self, message): now = int(time.time()) - with config.json_rw(self.config_path) as j: + with json_rw(self.config_path) as j: j['log'].append([now, message]) def status(self): diff --git a/amanuensis/lexicon/manage.py b/amanuensis/lexicon/manage.py index 06eec5f..237f4ae 100644 --- a/amanuensis/lexicon/manage.py +++ b/amanuensis/lexicon/manage.py @@ -9,10 +9,10 @@ import shutil import time import uuid -import config -from config.loader import AttrOrderedDict -import lexicon -import resources +from amanuensis.config import prepend, json_rw, json_ro, logger +from amanuensis.config.loader import AttrOrderedDict +from amanuensis.lexicon import LexiconModel +from amanuensis.resources import get_stream def valid_name(name): """ @@ -34,28 +34,28 @@ def create_lexicon(name, editor): # Create the lexicon directory and initialize it with a blank lexicon lid = uuid.uuid4().hex - lex_dir = config.prepend("lexicon", lid) + lex_dir = prepend("lexicon", lid) os.mkdir(lex_dir) - with resources.get_stream("lexicon.json") as s: - with open(config.prepend(lex_dir, 'config.json'), 'wb') as f: + with get_stream("lexicon.json") as s: + with open(prepend(lex_dir, 'config.json'), 'wb') as f: f.write(s.read()) # Fill out the new lexicon - with config.json_rw(lex_dir, 'config.json') as cfg: + with json_rw(lex_dir, 'config.json') as cfg: cfg['lid'] = lid cfg['name'] = name cfg['editor'] = editor.uid cfg['time']['created'] = int(time.time()) # Update the index with the new lexicon - with config.json_rw('lexicon', 'index.json') as index: + with json_rw('lexicon', 'index.json') as index: index[name] = lid # Load the Lexicon and log creation - l = lexicon.LexiconModel(lid) + l = LexiconModel(lid) l.log("Lexicon created") - config.logger.info("Created Lexicon {0.name}, ed. {1.displayname} ({0.id})".format( + logger.info("Created Lexicon {0.name}, ed. {1.displayname} ({0.id})".format( l, editor)) # Add the editor @@ -82,7 +82,7 @@ def delete_lexicon(lex, purge=False): raise ValueError("Invalid lexicon: '{}'".format(lex)) # Delete the lexicon from the index - with config.json_rw('lexicon', 'index.json') as j: + with json_rw('lexicon', 'index.json') as j: if lex.id in j: del j[lex.id] @@ -91,7 +91,7 @@ def delete_lexicon(lex, purge=False): raise NotImplementedError() # Delete the lexicon config - lex_path = config.prepend('lexicon', lex.id) + lex_path = prepend('lexicon', lex.id) shutil.rmtree(lex_path) @@ -100,11 +100,11 @@ def get_all_lexicons(): Loads each lexicon in the lexicon index """ # Get all the lexicon ids in the index - with config.json_ro('lexicon', 'index.json') as index: + with json_ro('lexicon', 'index.json') as index: lids = list(index.values()) # Load all of the lexicons - lexes = list(map(lambda id: lexicon.LexiconModel.by(lid=id), lids)) + lexes = list(map(lambda id: LexiconModel.by(lid=id), lids)) return lexes @@ -145,7 +145,7 @@ def add_player(lex, player): raise ValueError("Invalid player: '{}'".format(player)) # Idempotently add player - with config.json_rw(lex.config_path) as cfg: + with json_rw(lex.config_path) as cfg: if player.id not in cfg.join.joined: cfg.join.joined.append(player.id) # Log to the lexicon's log @@ -165,7 +165,7 @@ def remove_player(lex, player): raise ValueError("Can't remove the editor '{}' from lexicon '{}'".format(player.username, lex.name)) # Idempotently remove player - with config.json_rw(lex.config_path) as cfg: + with json_rw(lex.config_path) as cfg: if player.id in cfg.join.joined: cfg.join.joined.remove(player.id) @@ -190,7 +190,7 @@ def add_character(lex, player, charinfo={}): raise ValueError("Duplicate character name: '{}'".format(charinfo)) # Load the character template - with resources.get_stream('character.json') as template: + with get_stream('character.json') as template: character = json.load(template, object_pairs_hook=AttrOrderedDict) # Fill out the character's information @@ -200,7 +200,7 @@ def add_character(lex, player, charinfo={}): character.signature = charinfo.get("signature") or ("~" + character.name) # Add the character to the lexicon - with config.json_rw(lex.config_path) as cfg: + with json_rw(lex.config_path) as cfg: cfg.character.new(character.cid, character) @@ -221,5 +221,5 @@ def delete_character(lex, charname): char = matches[0] # Remove character from character list - with config.json_rw(lex.config_path) as cfg: + with json_rw(lex.config_path) as cfg: del cfg.character[char.cid] \ No newline at end of file diff --git a/amanuensis/server/__init__.py b/amanuensis/server/__init__.py index 668664f..7c6b8b7 100644 --- a/amanuensis/server/__init__.py +++ b/amanuensis/server/__init__.py @@ -3,15 +3,15 @@ import os from flask import Flask, render_template from flask_login import LoginManager -import config -from server.auth import get_bp as get_auth_bp -from server.home import get_bp as get_home_bp -from server.lexicon import get_bp as get_lex_bp +from amanuensis.config import get +from amanuensis.server.auth import get_bp as get_auth_bp +from amanuensis.server.home import get_bp as get_home_bp +from amanuensis.server.lexicon import get_bp as get_lex_bp # Flask app init -static_root = os.path.abspath(config.get("static_root")) +static_root = os.path.abspath(get("static_root")) app = Flask(__name__, template_folder="../templates", static_folder=static_root) -app.secret_key = bytes.fromhex(config.get('secret_key')) +app.secret_key = bytes.fromhex(get('secret_key')) app.jinja_options['trim_blocks'] = True app.jinja_options['lstrip_blocks'] = True diff --git a/amanuensis/server/auth.py b/amanuensis/server/auth.py index 780abf4..7896d0e 100644 --- a/amanuensis/server/auth.py +++ b/amanuensis/server/auth.py @@ -4,8 +4,8 @@ from wtforms import StringField, PasswordField, BooleanField, SubmitField from wtforms.validators import DataRequired from flask_login import current_user, login_user, logout_user, login_required -import config -from user import UserModel +from amanuensis.config import logger +from amanuensis.user import UserModel class LoginForm(FlaskForm): username = StringField('Username', validators=[DataRequired()]) @@ -30,7 +30,7 @@ def get_bp(login_manager): if u is not None and u.check_password(form.password.data): remember_me = form.remember.data login_user(u, remember=remember_me) - config.logger.info("Logged in user '{}' ({})".format( + logger.info("Logged in user '{}' ({})".format( u.username, u.uid)) return redirect(url_for('home.home')) flash("Login not recognized") diff --git a/amanuensis/server/home.py b/amanuensis/server/home.py index c2b76e0..6cc57ea 100644 --- a/amanuensis/server/home.py +++ b/amanuensis/server/home.py @@ -6,9 +6,7 @@ from flask_login import login_required, current_user from flask_wtf import FlaskForm from wtforms import TextAreaField, SubmitField, StringField -import config -import user -import lexicon +from amanuensis.config import json_ro class AdminDashboardForm(FlaskForm): lexiconName = StringField("Lexicon name") @@ -42,10 +40,10 @@ def get_bp(): if form.lexiconName.data: lid = None - with config.json_ro('lexicon', 'index.json') as index: + with json_ro('lexicon', 'index.json') as index: lid = index.get(form.lexiconName.data) if lid is not None: - with config.json_ro('lexicon', lid, 'config.json') as cfg: + with json_ro('lexicon', lid, 'config.json') as cfg: form.configText.data = json.dumps(cfg, indent=2) form.lexiconName.data = "" elif form.configText.data: diff --git a/amanuensis/server/lexicon.py b/amanuensis/server/lexicon.py index d9ed0f4..1586244 100644 --- a/amanuensis/server/lexicon.py +++ b/amanuensis/server/lexicon.py @@ -6,16 +6,16 @@ from flask_login import login_required, current_user from flask_wtf import FlaskForm from wtforms import TextAreaField, SubmitField -import config -from config.loader import ReadOnlyOrderedDict -import user -import lexicon +from amanuensis.config import json_ro, open_ex +from amanuensis.config.loader import ReadOnlyOrderedDict +from amanuensis.lexicon import LexiconModel +from amanuensis.user import UserModel def lexicon_param(route): @wraps(route) def with_lexicon(name): - g.lexicon = lexicon.LexiconModel.by(name=name) + g.lexicon = LexiconModel.by(name=name) if g.lexicon is None: flash("Couldn't find a lexicon with the name '{}'".format(name)) return redirect(url_for("home.home")) @@ -63,7 +63,7 @@ def get_bp(): # Load the config for the lexicon on load if not form.is_submitted(): - with config.json_ro(g.lexicon.config_path) as cfg: + with json_ro(g.lexicon.config_path) as cfg: form.configText.data = json.dumps(cfg, indent=2) return render_template("lexicon/session_edit.html", form=form) @@ -78,7 +78,7 @@ def get_bp(): # TODO # Write the new config form.submit.submitted = False - with config.open_ex(g.lexicon.config_path, mode='w') as f: + with open_ex(g.lexicon.config_path, mode='w') as f: json.dump(cfg, f, indent='\t') flash("Config updated") return redirect(url_for('lexicon.session_edit', name=name)) diff --git a/amanuensis/user.py b/amanuensis/user.py index eedb03a..f5af951 100644 --- a/amanuensis/user.py +++ b/amanuensis/user.py @@ -6,10 +6,10 @@ import uuid from flask_login import UserMixin from werkzeug.security import generate_password_hash, check_password_hash -from errors import InternalMisuseError, MissingConfigError, IndexMismatchError -import config -import resources -import lexicon.manage +from amanuensis.errors import InternalMisuseError, MissingConfigError, IndexMismatchError +from amanuensis.config import prepend, json_ro, json_rw +from amanuensis.resources import get_stream +from amanuensis.lexicon.manage import get_all_lexicons class UserModel(UserMixin): @staticmethod @@ -26,21 +26,21 @@ class UserModel(UserMixin): if not uid and not name: raise ValueError("One of uid or name must be not None") if not uid: - with config.json_ro('user', 'index.json') as index: + with json_ro('user', 'index.json') as index: uid = index.get(name) if not uid: return None - if not os.path.isdir(config.prepend('user', uid)): + if not os.path.isdir(prepend('user', uid)): raise IndexMismatchError("username={} uid={}".format(name, uid)) - if not os.path.isfile(config.prepend('user', uid, 'config.json')): + if not os.path.isfile(prepend('user', uid, 'config.json')): raise MissingConfigError("uid={}".format(uid)) return UserModel(uid) def __init__(self, uid): """User model initializer, assume all checks were done by by()""" self.id = str(uid) # Flask-Login checks for this - self.config_path = config.prepend('user', uid, 'config.json') - with config.json_ro(self.config_path) as j: + self.config_path = prepend('user', uid, 'config.json') + with json_ro(self.config_path) as j: self.config = j def __getattr__(self, key): @@ -50,17 +50,17 @@ class UserModel(UserMixin): def set_password(self, pw): h = generate_password_hash(pw) - with config.json_rw(self.config_path) as j: + with json_rw(self.config_path) as j: j['password'] = h def check_password(self, pw): - with config.json_ro(self.config_path) as j: + with json_ro(self.config_path) as j: return check_password_hash(j['password'], pw) def lexicons_in(self): return [ lex - for lex in lexicon.manage.get_all_lexicons() + for lex in get_all_lexicons() if self.id in lex.join.joined ] @@ -87,14 +87,14 @@ def create_user(username, displayname, email): # Create the user directory and initialize it with a blank user uid = uuid.uuid4().hex - user_dir = config.prepend("user", uid) + user_dir = prepend("user", uid) os.mkdir(user_dir) - with resources.get_stream("user.json") as s: - with open(config.prepend(user_dir, 'config.json'), 'wb') as f: + with get_stream("user.json") as s: + with open(prepend(user_dir, 'config.json'), 'wb') as f: f.write(s.read()) # Fill out the new user - with config.json_rw(user_dir, 'config.json') as cfg: + with json_rw(user_dir, 'config.json') as cfg: cfg.uid = uid cfg.username = username cfg.displayname = displayname @@ -102,7 +102,7 @@ def create_user(username, displayname, email): cfg.created = int(time.time()) # Update the index with the new user - with config.json_rw('user', 'index.json') as index: + with json_rw('user', 'index.json') as index: index[username] = uid # Set a temporary password