Merge pull request #8 from tomgalloway/master

Manage User & Groups pages now display correctly but don't do anything yet.
This commit is contained in:
Nick Daly 2013-01-21 17:49:13 -08:00
commit ba15a92023
8 changed files with 159 additions and 28 deletions

1
.gitignore vendored
View File

@ -25,3 +25,4 @@ cherrypy.config
data/users.sqlite3 data/users.sqlite3
predepend predepend
build/ build/
*.pid

View File

@ -1,14 +1,15 @@
class User(dict): class User(dict):
""" Every user must have keys for a username, name, password (this """ Every user must have keys for a username, name, passphrase (this
is a md5 hash of the password), groups, and an email address. They can be is a md5 hash of the password), groups, and an email address. They can be
blank or None, but the keys must exist. """ blank or None, but the keys must exist. """
def __init__(self, dict=None): def __init__(self, dict=None):
for key in ['username', 'name', 'password', 'email']: for key in ['username', 'name', 'passphrase', 'email']:
self[key] = '' self[key] = ''
for key in ['groups']: for key in ['groups']:
self[key] = [] self[key] = []
for key in dict: if dict:
self[key] = dict[key] for key in dict:
self[key] = dict[key]
def __getattr__(self, attr): def __getattr__(self, attr):
return None return None

View File

@ -12,10 +12,42 @@ class UserStore(UserStoreModule, sqlite_db):
self.db_file = cfg.user_db self.db_file = cfg.user_db
sqlite_db.__init__(self, self.db_file, autocommit=True) sqlite_db.__init__(self, self.db_file, autocommit=True)
self.__enter__() self.__enter__()
def close(self): def close(self):
self.__exit__() self.__exit__(None,None,None)
def expert(self):
return False def expert(self, username=None):
groups = self.attr(username,"groups")
if not groups:
return False
return 'expert' in groups
def attr(self, username=None, field=None):
return self.get(username)[field]
def get(self,username=None):
return User(sqlite_db.get(self,username))
def exists(self, username=None):
try:
user = self.get(username)
if not user:
return False
elif user["username"]=='':
return False
return True
except TypeError:
return False
def remove(self,username=None):
self.__delitem__(username)
self.commit()
def get_all(self):
return self.items()
def set(self,username=None,user=None):
sqlite_db.__setitem__(self,username, user)
class UserStoreOld(): class UserStoreOld():
#class UserStore(UserStoreModule): #class UserStore(UserStoreModule):

View File

@ -5,22 +5,23 @@ from plugin_mount import PagePlugin, FormPlugin
import cfg import cfg
from forms import Form from forms import Form
from util import * from util import *
from pprint import pprint
class users(PagePlugin): class users(PagePlugin):
order = 20 # order of running init in PagePlugins order = 20 # order of running init in PagePlugins
def __init__(self, *args, **kwargs): def __init__(self, *args, **kwargs):
PagePlugin.__init__(self, *args, **kwargs) PagePlugin.__init__(self, *args, **kwargs)
self.register_page("sys.users") self.register_page("sys.users")
self.register_page("sys.users.add")
self.register_page("sys.users.edit")
@cherrypy.expose @cherrypy.expose
@require() @require()
def index(self): def index(self):
parts = self.forms('/sys/config') return self.fill_template(title="Manage Users and Groups", sidebar_right="""<strong><a href="/sys/users/add">Add User</a></strong><br/><strong><a href="/sys/users/edit">Edit Users</a></strong>""")
parts['title']=_("Manage Users and Groups")
return self.fill_template(**parts)
class add(FormPlugin, PagePlugin): class add(FormPlugin, PagePlugin):
url = ["/sys/users"] url = ["/sys/users/add"]
order = 30 order = 30
sidebar_left = '' sidebar_left = ''
@ -46,27 +47,29 @@ class add(FormPlugin, PagePlugin):
return form.render() return form.render()
def process_form(self, username=None, name=None, email=None, md5_password=None, **kwargs): def process_form(self, username=None, name=None, email=None, md5_password=None, **kwargs):
msg = '' msg = Message()
if not username: msg = add_message(msg, _("Must specify a username!")) if not username: msg.add = _("Must specify a username!")
if not md5_password: msg = add_message(msg, _("Must specify a password!")) if not md5_password: msg.add = _("Must specify a password!")
if username in cfg.users: if username in cfg.users.keys():
msg = add_message(msg, _("User already exists!")) msg.add = _("User already exists!")
else: else:
try: try:
cfg.users[username]= User(dict={'username':username, 'name':name, 'email':email, 'password':md5_password}) di = {'username':username, 'name':name, 'email':email, 'passphrase':md5_password}
new_user = User(dict=di)
cfg.users.set(username,new_user)
except: except:
msg = add_message(msg, _("Error storing user!")) msg.add = _("Error storing user!")
if not msg: if not msg:
msg = add_message(msg, "%s saved." % username) msg.add = _("%s saved." % username)
cfg.log(msg.text)
main = self.make_form(username, name, email, message=msg) #main = self.make_form(username, name, email, msg=msg.text)
return self.fill_template(title="", main=main, sidebar_left=self.sidebar_left, sidebar_right=self.sidebar_right) return self.fill_template(title="Manage Users and Groups", main=main, sidebar_left=self.sidebar_left, sidebar_right=self.sidebar_right)
class edit(FormPlugin, PagePlugin): class edit(FormPlugin, PagePlugin):
url = ["/sys/users"] url = ["/sys/users/edit"]
order = 35 order = 35
sidebar_left = '' sidebar_left = ''
@ -77,7 +80,7 @@ class edit(FormPlugin, PagePlugin):
system.</p><p>Deleting users is permanent!</p>""" % (cfg.product_name, cfg.box_name)) system.</p><p>Deleting users is permanent!</p>""" % (cfg.product_name, cfg.box_name))
def main(self, msg=''): def main(self, msg=''):
users = cfg.users.keys() users = cfg.users
add_form = Form(title=_("Edit or Delete User"), action="/sys/users/edit", message=msg) add_form = Form(title=_("Edit or Delete User"), action="/sys/users/edit", message=msg)
add_form.html('<span class="indent"><strong>Delete</strong><br /></span>') add_form.html('<span class="indent"><strong>Delete</strong><br /></span>')
for uname in sorted(users.keys()): for uname in sorted(users.keys()):
@ -113,8 +116,8 @@ class edit(FormPlugin, PagePlugin):
msg.add(_("User %s does not exist." % username)) msg.add(_("User %s does not exist." % username))
else: else:
msg.add = _("Must specify at least one valid, existing user.") msg.add = _("Must specify at least one valid, existing user.")
main = self.make_form(msg=msg.text) #main = self.make_form(msg=msg.text)
return self.fill_template(title="", main=main, sidebar_left=self.sidebar_left, sidebar_right=self.sidebar_right) return self.fill_template(title="Manage Users and Groups", main=main, sidebar_left=self.sidebar_left, sidebar_right=self.sidebar_right)
sidebar_right = '' sidebar_right = ''
u = cfg.users[kwargs['username']] u = cfg.users[kwargs['username']]
@ -125,4 +128,4 @@ class edit(FormPlugin, PagePlugin):
main = _("""<strong>Edit User '%s'</strong>""" % u['username']) main = _("""<strong>Edit User '%s'</strong>""" % u['username'])
sidebar_right = '' sidebar_right = ''
return self.fill_template(title="", main=main, sidebar_left=self.sidebar_left, sidebar_right=sidebar_right) return self.fill_template(title="Manage Users and Groups", main=main, sidebar_left=self.sidebar_left, sidebar_right=sidebar_right)

View File

@ -1,7 +1,6 @@
#! /bin/sh #! /bin/sh
PYTHONPATH=build/exmachina:$PYTHONPATH PYTHONPATH=build/exmachina:$PYTHONPATH
PYTHONPATH=build/bjsonrpc:$PYTHONPATH
export PYTHONPATH export PYTHONPATH

9
test.sh Executable file
View File

@ -0,0 +1,9 @@
#! /bin/sh
PYTHONPATH=build/exmachina:$PYTHONPATH
PYTHONPATH=modules/installed/lib:$PYTHONPATH
PYTHONPATH=vendor:$PYTHONPATH
export PYTHONPATH
python tests/test_user_store.py

86
tests/test_user_store.py Normal file
View File

@ -0,0 +1,86 @@
#! /usr/bin/env python
# -*- mode: python; mode: auto-fill; fill-column: 80 -*-
import user_store
from logger import Logger
import cfg
import unittest
import cherrypy
import plugin_mount
import os
from model import User
cfg.log = Logger()
cherrypy.log.access_file = None
class UserStore(unittest.TestCase):
"""Test each function of user_store to confirm they work as expected"""
def setUp(self):
cfg.user_db = os.path.join(cfg.file_root, "tests/testdata/users");
self.userstore = plugin_mount.UserStoreModule.get_plugins()[0]
def tearDown(self):
for user in self.userstore.get_all():
self.userstore.remove(user[0])
self.userstore.close()
def test_user_does_not_exist(self):
self.assertEqual(self.userstore.exists("notausername"),False)
def test_user_does_exist(self):
self.add_user("isausername", False)
self.assertEqual(self.userstore.exists("isausername"),True)
def test_add_user(self):
self.assertEqual(len(self.userstore.items()),0)
self.add_user("test_user", False)
self.assertEqual(len(self.userstore.items()),1)
def test_user_is_in_expert_group(self):
self.add_user("test_user", True)
self.assertEqual(self.userstore.expert("test_user"),True)
def test_user_is_not_in_expert_group(self):
self.add_user("test_user", False)
self.assertEqual(self.userstore.expert("test_user"),False)
def test_user_removal(self):
self.assertEqual(len(self.userstore.items()),0)
self.add_user("test_user", False)
self.assertEqual(len(self.userstore.items()),1)
self.userstore.remove("test_user")
self.assertEqual(len(self.userstore.items()),0)
def test_get_user_email_attribute(self):
self.add_user("test_user", False,"test@home")
self.assertEqual(self.userstore.attr("test_user","email"),"test@home")
def test_get_user(self):
test_user = self.add_user("test_user", False)
self.assertEqual(self.userstore.get("test_user"),test_user)
def test_get_all_users(self):
self.add_user("test_user1", False)
self.add_user("test_user2", False)
self.assertEqual(len(self.userstore.get_all()),2)
def add_user(self, test_username, add_to_expert_group, email=''):
test_user = self.create_user(test_username, email)
if add_to_expert_group:
test_user = self.add_user_to_expert_group(test_user)
self.userstore.set(test_username,test_user)
return test_user
def create_user(self, username, email=''):
test_user = User()
test_user["username"] = username
test_user["email"] = email
return test_user
def add_user_to_expert_group(self, user):
user["groups"] = ["expert"]
return user
if __name__ == "__main__":
unittest.main()

BIN
tests/testdata/users.sqlite3 vendored Normal file

Binary file not shown.