diff --git a/CONTRIBUTORS b/CONTRIBUTORS --- a/CONTRIBUTORS +++ b/CONTRIBUTORS @@ -33,3 +33,4 @@ List of contributors to RhodeCode projec Philip Jameson Mads Kiilerich Dan Sheridan + Dennis Brakhane diff --git a/README.rst b/README.rst --- a/README.rst +++ b/README.rst @@ -75,7 +75,7 @@ RhodeCode Features - Supports http/https, LDAP, AD, proxy-pass authentication. - Full permissions (private/read/write/admin) together with IP restrictions for each repository, additional explicit forking and repository creation permissions. -- Users groups for easier permission management +- User groups for easier permission management - Repository groups let you group repos and manage them easier. - Users can fork other users repos, and compare them at any time. - Integrates easily with other systems, with custom created mappers you can connect it to almost diff --git a/docs/api/api.rst b/docs/api/api.rst --- a/docs/api/api.rst +++ b/docs/api/api.rst @@ -436,7 +436,7 @@ OUTPUT:: get_users_group --------------- -Gets an existing users group. This command can be executed only using api_key +Gets an existing user group. This command can be executed only using api_key belonging to user with admin rights. @@ -446,7 +446,7 @@ INPUT:: api_key : "" method : "get_users_group" args : { - "usersgroupid" : "" + "usersgroupid" : "" } OUTPUT:: @@ -479,7 +479,7 @@ OUTPUT:: get_users_groups ---------------- -Lists all existing users groups. This command can be executed only using +Lists all existing user groups. This command can be executed only using api_key belonging to user with admin rights. @@ -507,7 +507,7 @@ OUTPUT:: create_users_group ------------------ -Creates new users group. This command can be executed only using api_key +Creates new user group. This command can be executed only using api_key belonging to user with admin rights @@ -525,7 +525,7 @@ OUTPUT:: id : result: { - "msg": "created new users group ``", + "msg": "created new user group ``", "users_group": { "users_group_id" : "", "group_name" : "", @@ -538,7 +538,7 @@ OUTPUT:: add_user_to_users_group ----------------------- -Adds a user to a users group. If user exists in that group success will be +Adds a user to a user group. If user exists in that group success will be `false`. This command can be executed only using api_key belonging to user with admin rights @@ -549,7 +549,7 @@ INPUT:: api_key : "" method : "add_user_users_group" args: { - "usersgroupid" : "", + "usersgroupid" : "", "userid" : "", } @@ -558,7 +558,7 @@ OUTPUT:: id : result: { "success": True|False # depends on if member is in group - "msg": "added member `` to users group `` | + "msg": "added member `` to user group `` | User is already in that group" } error: null @@ -567,7 +567,7 @@ OUTPUT:: remove_user_from_users_group ---------------------------- -Removes a user from a users group. If user is not in given group success will +Removes a user from a user group. If user is not in given group success will be `false`. This command can be executed only using api_key belonging to user with admin rights @@ -578,7 +578,7 @@ INPUT:: api_key : "" method : "remove_user_from_users_group" args: { - "usersgroupid" : "", + "usersgroupid" : "", "userid" : "", } @@ -587,7 +587,7 @@ OUTPUT:: id : result: { "success": True|False, # depends on if member is in group - "msg": "removed member from users group | + "msg": "removed member from user group | User wasn't in group" } error: null @@ -929,7 +929,7 @@ OUTPUT:: grant_users_group_permission ---------------------------- -Grant permission for users group on given repository, or update +Grant permission for user group on given repository, or update existing one if found. This command can be executed only using api_key belonging to user with admin rights. @@ -941,7 +941,7 @@ INPUT:: method : "grant_users_group_permission" args: { "repoid" : "" - "usersgroupid" : "" + "usersgroupid" : "" "perm" : "(repository.(none|read|write|admin))", } @@ -958,7 +958,7 @@ OUTPUT:: revoke_users_group_permission ----------------------------- -Revoke permission for users group on given repository.This command can be +Revoke permission for user group on given repository.This command can be executed only using api_key belonging to user with admin rights. INPUT:: @@ -968,7 +968,7 @@ INPUT:: method : "revoke_users_group_permission" args: { "repoid" : "" - "usersgroupid" : "" + "usersgroupid" : "" } OUTPUT:: diff --git a/docs/changelog.rst b/docs/changelog.rst --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -196,7 +196,7 @@ news fixes +++++ -- fixed #570 explicit users group permissions can overwrite owner permissions +- fixed #570 explicit user group permissions can overwrite owner permissions - fixed #578 set proper PATH with current Python for Git hooks to execute within same Python as RhodeCode - fixed issue with Git bare repos that ends with .git in name @@ -385,7 +385,7 @@ news - created rcextensions module with additional mappings (ref #322) and post push/pull/create repo hooks callbacks - implemented #377 Users view for his own permissions on account page -- #399 added inheritance of permissions for users group on repos groups +- #399 added inheritance of permissions for user group on repos groups - #401 repository group is automatically pre-selected when adding repos inside a repository group - added alternative HTTP 403 response when client failed to authenticate. Helps @@ -520,7 +520,7 @@ fixes and groups - fixes #271 rare JSON serialization problem with statistics - fixes #337 missing validation check for conflicting names of a group with a - repositories group + repository group - #340 fixed session problem for mysql and celery tasks - fixed #331 RhodeCode mangles repository names if the a repository group contains the "full path" to the repositories @@ -654,7 +654,7 @@ news - implemented #93 customizable changelog on combined revision ranges - equivalent of githubs compare view - implemented #108 extended and more powerful LDAP configuration -- implemented #56 users groups +- implemented #56 user groups - major code rewrites optimized codes for speed and memory usage - raw and diff downloads are now in git format - setup command checks for write access to given path diff --git a/docs/installation_win.rst b/docs/installation_win.rst --- a/docs/installation_win.rst +++ b/docs/installation_win.rst @@ -47,7 +47,7 @@ choose "Visual C++ 2008 Express" when in required, you can uncheck them .. note:: - + 64bit: You also need to install the Microsoft Windows SDK for .NET 3.5 SP1 (.NET 4.0 won't work). Download from: http://www.microsoft.com/en-us/download/details.aspx?id=3138 @@ -90,7 +90,7 @@ http://sourceforge.net/projects/pywin32/ .. note:: 64bit: Download and install the 64bit version. - At the time of writing you can find this at: + At the time of writing you can find this at: http://sourceforge.net/projects/pywin32/files/pywin32/Build%20218/pywin32-218.win-amd64-py2.7.exe/download Step4 - Python BIN diff --git a/docs/theme/nature/static/pygments.css b/docs/theme/nature/static/pygments.css --- a/docs/theme/nature/static/pygments.css +++ b/docs/theme/nature/static/pygments.css @@ -51,4 +51,4 @@ .vc { color: #ff99ff } /* Name.Variable.Class */ .vg { color: #ff99ff } /* Name.Variable.Global */ .vi { color: #ff99ff } /* Name.Variable.Instance */ -.il { color: #009999 } /* Literal.Number.Integer.Long */ \ No newline at end of file +.il { color: #009999 } /* Literal.Number.Integer.Long */ diff --git a/docs/usage/performance.rst b/docs/usage/performance.rst --- a/docs/usage/performance.rst +++ b/docs/usage/performance.rst @@ -46,19 +46,17 @@ Follow these few steps to improve perfor large traffic (large amount of users, CI servers etc). RhodeCode can be scaled horizontally on one (recommended) or multiple machines. In order to scale horizontally you need to do the following: - + - each instance needs it's own .ini file and unique `instance_id` set in them - - each instance `data` storage needs to be configured to be stored on a + - each instance `data` storage needs to be configured to be stored on a shared disk storage, preferably together with repositories. This `data` dir contains template caches, sessions, whoosh index and it's used for tasks locking (so it's safe across multiple instances). Set the `cache_dir`, `index_dir`, `beaker.cache.data_dir`, `beaker.cache.lock_dir` - variables in each .ini file to shared location across RhodeCode instances + variables in each .ini file to shared location across RhodeCode instances - if celery is used each instance should run separate celery instance, but the message broken should be common to all of them (ex one rabbitmq - shared server) + shared server) - load balance using round robin or ip hash, recommended is writing LB rules that will separate regular user traffic from automated processes like CI servers or build bots. - - diff --git a/requires.txt b/requires.txt deleted file mode 100644 --- a/requires.txt +++ /dev/null @@ -1,20 +0,0 @@ -waitress==0.8.1 -webob==1.0.8 -Pylons==1.0.0 -Beaker==1.6.4 -WebHelpers==1.3 -formencode==1.2.4 -SQLAlchemy==0.7.8 -Mako==0.7.2 -pygments>=1.5 -whoosh>=2.4.0,<2.5 -celery>=2.2.5,<2.3 -babel -python-dateutil>=1.5.0,<2.0.0 -dulwich>=0.8.5,<0.9.0 -markdown==2.1.1 -docutils==0.8.1 -simplejson==2.5.2 -mock -py-bcrypt -mercurial==2.3.0 \ No newline at end of file diff --git a/rhodecode/config/routing.py b/rhodecode/config/routing.py --- a/rhodecode/config/routing.py +++ b/rhodecode/config/routing.py @@ -48,7 +48,7 @@ def make_map(config): def check_group(environ, match_dict): """ - check for valid repositories group for proper 404 handling + check for valid repository group for proper 404 handling :param environ: :param match_dict: @@ -235,7 +235,7 @@ def make_map(config): m.connect("user_ips_delete", "/users_ips/{id}", action="delete_ip", conditions=dict(method=["DELETE"])) - #ADMIN USERS GROUPS REST ROUTES + #ADMIN USER GROUPS REST ROUTES with rmap.submapper(path_prefix=ADMIN_PREFIX, controller='admin/users_groups') as m: m.connect("users_groups", "/users_groups", diff --git a/rhodecode/controllers/admin/notifications.py b/rhodecode/controllers/admin/notifications.py --- a/rhodecode/controllers/admin/notifications.py +++ b/rhodecode/controllers/admin/notifications.py @@ -28,7 +28,7 @@ import traceback from pylons import request from pylons import tmpl_context as c, url -from pylons.controllers.util import redirect +from pylons.controllers.util import redirect, abort from webhelpers.paginate import Page @@ -117,7 +117,7 @@ class NotificationsController(BaseContro Session().commit() return 'ok' except Exception: - Session.rollback() + Session().rollback() log.error(traceback.format_exc()) return 'fail' @@ -139,7 +139,7 @@ class NotificationsController(BaseContro Session().commit() return 'ok' except Exception: - Session.rollback() + Session().rollback() log.error(traceback.format_exc()) return 'fail' @@ -149,8 +149,9 @@ class NotificationsController(BaseContro c.user = self.rhodecode_user no = Notification.get(notification_id) - owner = all(un.user.user_id == c.rhodecode_user.user_id + owner = any(un.user.user_id == c.rhodecode_user.user_id for un in no.notifications_to_users) + if no and (h.HasPermissionAny('hg.admin', 'repository.admin')() or owner): unotification = NotificationModel()\ .get_user_notification(c.user.user_id, no) @@ -165,7 +166,7 @@ class NotificationsController(BaseContro return render('admin/notifications/show_notification.html') - return redirect(url('notifications')) + return abort(403) def edit(self, notification_id, format='html'): """GET /_admin/notifications/id/edit: Form to edit an existing item""" diff --git a/rhodecode/controllers/admin/repos.py b/rhodecode/controllers/admin/repos.py --- a/rhodecode/controllers/admin/repos.py +++ b/rhodecode/controllers/admin/repos.py @@ -345,7 +345,7 @@ class ReposController(BaseRepoController @HasRepoPermissionAllDecorator('repository.admin') def delete_perm_users_group(self, repo_name): """ - DELETE an existing repository permission users group + DELETE an existing repository permission user group :param repo_name: """ @@ -358,7 +358,7 @@ class ReposController(BaseRepoController except Exception: log.error(traceback.format_exc()) h.flash(_('An error occurred during deletion of repository' - ' users groups'), + ' user groups'), category='error') raise HTTPInternalServerError() diff --git a/rhodecode/controllers/admin/repos_groups.py b/rhodecode/controllers/admin/repos_groups.py --- a/rhodecode/controllers/admin/repos_groups.py +++ b/rhodecode/controllers/admin/repos_groups.py @@ -3,7 +3,7 @@ rhodecode.controllers.admin.repos_groups ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - Repositories groups controller for RhodeCode + Repository groups controller for RhodeCode :created_on: Mar 23, 2010 :author: marcink @@ -282,7 +282,7 @@ class ReposGroupsController(BaseControll @HasReposGroupPermissionAnyDecorator('group.admin') def delete_repos_group_user_perm(self, group_name): """ - DELETE an existing repositories group permission user + DELETE an existing repository group permission user :param group_name: """ @@ -307,7 +307,7 @@ class ReposGroupsController(BaseControll @HasReposGroupPermissionAnyDecorator('group.admin') def delete_repos_group_users_group_perm(self, group_name): """ - DELETE an existing repositories group permission users group + DELETE an existing repository group permission user group :param group_name: """ @@ -322,7 +322,7 @@ class ReposGroupsController(BaseControll except Exception: log.error(traceback.format_exc()) h.flash(_('An error occurred during deletion of group' - ' users groups'), + ' user groups'), category='error') raise HTTPInternalServerError() diff --git a/rhodecode/controllers/admin/settings.py b/rhodecode/controllers/admin/settings.py --- a/rhodecode/controllers/admin/settings.py +++ b/rhodecode/controllers/admin/settings.py @@ -474,18 +474,23 @@ class SettingsController(BaseController) @NotAnonymous() def my_account_my_pullrequests(self): - c.my_pull_requests = PullRequest.query()\ + c.show_closed = request.GET.get('pr_show_closed') + + def _filter(pr): + s = sorted(pr, key=lambda o: o.created_on, reverse=True) + if not c.show_closed: + s = filter(lambda p: p.status != PullRequest.STATUS_CLOSED, s) + return s + + c.my_pull_requests = _filter(PullRequest.query()\ .filter(PullRequest.user_id == self.rhodecode_user.user_id)\ - .order_by(PullRequest.created_on.desc())\ - .all() + .all()) - c.participate_in_pull_requests = sorted( - [x.pull_request for x in PullRequestReviewers.query()\ - .filter(PullRequestReviewers.user_id == - self.rhodecode_user.user_id)\ - .all()], - key=lambda o: o.created_on, reverse=True) + c.participate_in_pull_requests = _filter([ + x.pull_request for x in PullRequestReviewers.query()\ + .filter(PullRequestReviewers.user_id == + self.rhodecode_user.user_id).all()]) return render('admin/users/user_edit_my_account_pullrequests.html') diff --git a/rhodecode/controllers/admin/users_groups.py b/rhodecode/controllers/admin/users_groups.py --- a/rhodecode/controllers/admin/users_groups.py +++ b/rhodecode/controllers/admin/users_groups.py @@ -3,7 +3,7 @@ rhodecode.controllers.admin.users_groups ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - Users Groups crud controller for pylons + User Groups crud controller for pylons :created_on: Jan 25, 2011 :author: marcink @@ -33,16 +33,16 @@ from pylons.controllers.util import abor from pylons.i18n.translation import _ from rhodecode.lib import helpers as h -from rhodecode.lib.exceptions import UsersGroupsAssignedException +from rhodecode.lib.exceptions import UserGroupsAssignedException from rhodecode.lib.utils2 import safe_unicode, str2bool from rhodecode.lib.auth import LoginRequired, HasPermissionAllDecorator from rhodecode.lib.base import BaseController, render -from rhodecode.model.users_group import UsersGroupModel +from rhodecode.model.users_group import UserGroupModel -from rhodecode.model.db import User, UsersGroup, UsersGroupToPerm,\ - UsersGroupRepoToPerm, UsersGroupRepoGroupToPerm -from rhodecode.model.forms import UsersGroupForm +from rhodecode.model.db import User, UserGroup, UserGroupToPerm,\ + UserGroupRepoToPerm, UserGroupRepoGroupToPerm +from rhodecode.model.forms import UserGroupForm from rhodecode.model.meta import Session from rhodecode.lib.utils import action_logger from sqlalchemy.orm import joinedload @@ -67,23 +67,23 @@ class UsersGroupsController(BaseControll def index(self, format='html'): """GET /users_groups: All items in the collection""" # url('users_groups') - c.users_groups_list = UsersGroup().query().all() + c.users_groups_list = UserGroup().query().all() return render('admin/users_groups/users_groups.html') def create(self): """POST /users_groups: Create a new item""" # url('users_groups') - users_group_form = UsersGroupForm()() + users_group_form = UserGroupForm()() try: form_result = users_group_form.to_python(dict(request.POST)) - UsersGroupModel().create(name=form_result['users_group_name'], + UserGroupModel().create(name=form_result['users_group_name'], active=form_result['users_group_active']) gr = form_result['users_group_name'] action_logger(self.rhodecode_user, 'admin_created_users_group:%s' % gr, None, self.ip_addr, self.sa) - h.flash(_('created users group %s') % gr, category='success') + h.flash(_('created user group %s') % gr, category='success') Session().commit() except formencode.Invalid, errors: return htmlfill.render( @@ -94,7 +94,7 @@ class UsersGroupsController(BaseControll encoding="UTF-8") except Exception: log.error(traceback.format_exc()) - h.flash(_('error occurred during creation of users group %s') \ + h.flash(_('error occurred during creation of user group %s') \ % request.POST.get('users_group_name'), category='error') return redirect(url('users_groups')) @@ -110,20 +110,20 @@ class UsersGroupsController(BaseControll 'repositories_groups': {} } - ugroup_repo_perms = UsersGroupRepoToPerm.query()\ - .options(joinedload(UsersGroupRepoToPerm.permission))\ - .options(joinedload(UsersGroupRepoToPerm.repository))\ - .filter(UsersGroupRepoToPerm.users_group_id == id)\ + ugroup_repo_perms = UserGroupRepoToPerm.query()\ + .options(joinedload(UserGroupRepoToPerm.permission))\ + .options(joinedload(UserGroupRepoToPerm.repository))\ + .filter(UserGroupRepoToPerm.users_group_id == id)\ .all() for gr in ugroup_repo_perms: c.users_group.permissions['repositories'][gr.repository.repo_name] \ = gr.permission.permission_name - ugroup_group_perms = UsersGroupRepoGroupToPerm.query()\ - .options(joinedload(UsersGroupRepoGroupToPerm.permission))\ - .options(joinedload(UsersGroupRepoGroupToPerm.group))\ - .filter(UsersGroupRepoGroupToPerm.users_group_id == id)\ + ugroup_group_perms = UserGroupRepoGroupToPerm.query()\ + .options(joinedload(UserGroupRepoGroupToPerm.permission))\ + .options(joinedload(UserGroupRepoGroupToPerm.group))\ + .filter(UserGroupRepoGroupToPerm.users_group_id == id)\ .all() for gr in ugroup_group_perms: @@ -145,26 +145,26 @@ class UsersGroupsController(BaseControll # method='put') # url('users_group', id=ID) - c.users_group = UsersGroup.get_or_404(id) + c.users_group = UserGroup.get_or_404(id) self._load_data(id) available_members = [safe_unicode(x[0]) for x in c.available_members] - users_group_form = UsersGroupForm(edit=True, + users_group_form = UserGroupForm(edit=True, old_data=c.users_group.get_dict(), available_members=available_members)() try: form_result = users_group_form.to_python(request.POST) - UsersGroupModel().update(c.users_group, form_result) + UserGroupModel().update(c.users_group, form_result) gr = form_result['users_group_name'] action_logger(self.rhodecode_user, 'admin_updated_users_group:%s' % gr, None, self.ip_addr, self.sa) - h.flash(_('updated users group %s') % gr, category='success') + h.flash(_('updated user group %s') % gr, category='success') Session().commit() except formencode.Invalid, errors: - ug_model = UsersGroupModel() + ug_model = UserGroupModel() defaults = errors.value e = errors.error_dict or {} defaults.update({ @@ -183,7 +183,7 @@ class UsersGroupsController(BaseControll encoding="UTF-8") except Exception: log.error(traceback.format_exc()) - h.flash(_('error occurred during update of users group %s') \ + h.flash(_('error occurred during update of user group %s') \ % request.POST.get('users_group_name'), category='error') return redirect(url('edit_users_group', id=id)) @@ -196,16 +196,16 @@ class UsersGroupsController(BaseControll # h.form(url('users_group', id=ID), # method='delete') # url('users_group', id=ID) - usr_gr = UsersGroup.get_or_404(id) + usr_gr = UserGroup.get_or_404(id) try: - UsersGroupModel().delete(usr_gr) + UserGroupModel().delete(usr_gr) Session().commit() - h.flash(_('successfully deleted users group'), category='success') - except UsersGroupsAssignedException, e: + h.flash(_('successfully deleted user group'), category='success') + except UserGroupsAssignedException, e: h.flash(e, category='error') except Exception: log.error(traceback.format_exc()) - h.flash(_('An error occurred during deletion of users group'), + h.flash(_('An error occurred during deletion of user group'), category='error') return redirect(url('users_groups')) @@ -217,10 +217,10 @@ class UsersGroupsController(BaseControll """GET /users_groups/id/edit: Form to edit an existing item""" # url('edit_users_group', id=ID) - c.users_group = UsersGroup.get_or_404(id) + c.users_group = UserGroup.get_or_404(id) self._load_data(id) - ug_model = UsersGroupModel() + ug_model = UserGroupModel() defaults = c.users_group.get_dict() defaults.update({ 'create_repo_perm': ug_model.has_perm(c.users_group, @@ -240,37 +240,37 @@ class UsersGroupsController(BaseControll """PUT /users_perm/id: Update an existing item""" # url('users_group_perm', id=ID, method='put') - users_group = UsersGroup.get_or_404(id) + users_group = UserGroup.get_or_404(id) grant_create_perm = str2bool(request.POST.get('create_repo_perm')) grant_fork_perm = str2bool(request.POST.get('fork_repo_perm')) inherit_perms = str2bool(request.POST.get('inherit_default_permissions')) - usersgroup_model = UsersGroupModel() + usergroup_model = UserGroupModel() try: users_group.inherit_default_permissions = inherit_perms Session().add(users_group) if grant_create_perm: - usersgroup_model.revoke_perm(id, 'hg.create.none') - usersgroup_model.grant_perm(id, 'hg.create.repository') - h.flash(_("Granted 'repository create' permission to users group"), + usergroup_model.revoke_perm(id, 'hg.create.none') + usergroup_model.grant_perm(id, 'hg.create.repository') + h.flash(_("Granted 'repository create' permission to user group"), category='success') else: - usersgroup_model.revoke_perm(id, 'hg.create.repository') - usersgroup_model.grant_perm(id, 'hg.create.none') - h.flash(_("Revoked 'repository create' permission to users group"), + usergroup_model.revoke_perm(id, 'hg.create.repository') + usergroup_model.grant_perm(id, 'hg.create.none') + h.flash(_("Revoked 'repository create' permission to user group"), category='success') if grant_fork_perm: - usersgroup_model.revoke_perm(id, 'hg.fork.none') - usersgroup_model.grant_perm(id, 'hg.fork.repository') - h.flash(_("Granted 'repository fork' permission to users group"), + usergroup_model.revoke_perm(id, 'hg.fork.none') + usergroup_model.grant_perm(id, 'hg.fork.repository') + h.flash(_("Granted 'repository fork' permission to user group"), category='success') else: - usersgroup_model.revoke_perm(id, 'hg.fork.repository') - usersgroup_model.grant_perm(id, 'hg.fork.none') - h.flash(_("Revoked 'repository fork' permission to users group"), + usergroup_model.revoke_perm(id, 'hg.fork.repository') + usergroup_model.grant_perm(id, 'hg.fork.none') + h.flash(_("Revoked 'repository fork' permission to user group"), category='success') Session().commit() diff --git a/rhodecode/controllers/api/api.py b/rhodecode/controllers/api/api.py --- a/rhodecode/controllers/api/api.py +++ b/rhodecode/controllers/api/api.py @@ -34,11 +34,12 @@ from rhodecode.lib.auth import PasswordG HasPermissionAllDecorator, HasPermissionAnyDecorator, \ HasPermissionAnyApi, HasRepoPermissionAnyApi from rhodecode.lib.utils import map_groups, repo2db_mapper +from rhodecode.lib.utils2 import str2bool from rhodecode.model.meta import Session from rhodecode.model.scm import ScmModel from rhodecode.model.repo import RepoModel from rhodecode.model.user import UserModel -from rhodecode.model.users_group import UsersGroupModel +from rhodecode.model.users_group import UserGroupModel from rhodecode.model.permission import PermissionModel from rhodecode.model.db import Repository, RhodeCodeSetting, UserIpMap @@ -121,13 +122,13 @@ def get_repo_or_error(repoid): def get_users_group_or_error(usersgroupid): """ - Get users group by id or name or return JsonRPCError if not found + Get user group by id or name or return JsonRPCError if not found :param userid: """ - users_group = UsersGroupModel().get_group(usersgroupid) + users_group = UserGroupModel().get_group(usersgroupid) if users_group is None: - raise JSONRPCError('users group `%s` does not exist' % usersgroupid) + raise JSONRPCError('user group `%s` does not exist' % usersgroupid) return users_group @@ -257,7 +258,7 @@ class ApiController(JSONRPCController): if isinstance(userid, Optional): userid = apiuser.user_id user = get_user_or_error(userid) - locked = bool(locked) + locked = str2bool(locked) try: if locked: Repository.lock(repo, user.user_id) @@ -449,7 +450,7 @@ class ApiController(JSONRPCController): @HasPermissionAllDecorator('hg.admin') def get_users_group(self, apiuser, usersgroupid): """" - Get users group by name or id + Get user group by name or id :param apiuser: :param usersgroupid: @@ -468,13 +469,13 @@ class ApiController(JSONRPCController): @HasPermissionAllDecorator('hg.admin') def get_users_groups(self, apiuser): """" - Get all users groups + Get all user groups :param apiuser: """ result = [] - for users_group in UsersGroupModel().get_all(): + for users_group in UserGroupModel().get_all(): result.append(users_group.get_api_data()) return result @@ -488,15 +489,15 @@ class ApiController(JSONRPCController): :param active: """ - if UsersGroupModel().get_by_name(group_name): - raise JSONRPCError("users group `%s` already exist" % group_name) + if UserGroupModel().get_by_name(group_name): + raise JSONRPCError("user group `%s` already exist" % group_name) try: active = Optional.extract(active) - ug = UsersGroupModel().create(name=group_name, active=active) + ug = UserGroupModel().create(name=group_name, active=active) Session().commit() return dict( - msg='created new users group `%s`' % group_name, + msg='created new user group `%s`' % group_name, users_group=ug.get_api_data() ) except Exception: @@ -506,7 +507,7 @@ class ApiController(JSONRPCController): @HasPermissionAllDecorator('hg.admin') def add_user_to_users_group(self, apiuser, usersgroupid, userid): """" - Add a user to a users group + Add a user to a user group :param apiuser: :param usersgroupid: @@ -516,9 +517,9 @@ class ApiController(JSONRPCController): users_group = get_users_group_or_error(usersgroupid) try: - ugm = UsersGroupModel().add_user_to_group(users_group, user) + ugm = UserGroupModel().add_user_to_group(users_group, user) success = True if ugm != True else False - msg = 'added member `%s` to users group `%s`' % ( + msg = 'added member `%s` to user group `%s`' % ( user.username, users_group.users_group_name ) msg = msg if success else 'User is already in that group' @@ -531,7 +532,7 @@ class ApiController(JSONRPCController): except Exception: log.error(traceback.format_exc()) raise JSONRPCError( - 'failed to add member to users group `%s`' % ( + 'failed to add member to user group `%s`' % ( users_group.users_group_name ) ) @@ -549,9 +550,9 @@ class ApiController(JSONRPCController): users_group = get_users_group_or_error(usersgroupid) try: - success = UsersGroupModel().remove_user_from_group(users_group, + success = UserGroupModel().remove_user_from_group(users_group, user) - msg = 'removed member `%s` from users group `%s`' % ( + msg = 'removed member `%s` from user group `%s`' % ( user.username, users_group.users_group_name ) msg = msg if success else "User wasn't in group" @@ -560,7 +561,7 @@ class ApiController(JSONRPCController): except Exception: log.error(traceback.format_exc()) raise JSONRPCError( - 'failed to remove member from users group `%s`' % ( + 'failed to remove member from user group `%s`' % ( users_group.users_group_name ) ) @@ -890,7 +891,7 @@ class ApiController(JSONRPCController): def grant_users_group_permission(self, apiuser, repoid, usersgroupid, perm): """ - Grant permission for users group on given repository, or update + Grant permission for user group on given repository, or update existing one if found :param apiuser: @@ -909,7 +910,7 @@ class ApiController(JSONRPCController): Session().commit() return dict( - msg='Granted perm: `%s` for users group: `%s` in ' + msg='Granted perm: `%s` for user group: `%s` in ' 'repo: `%s`' % ( perm.permission_name, users_group.users_group_name, repo.repo_name @@ -919,7 +920,7 @@ class ApiController(JSONRPCController): except Exception: log.error(traceback.format_exc()) raise JSONRPCError( - 'failed to edit permission for users group: `%s` in ' + 'failed to edit permission for user group: `%s` in ' 'repo: `%s`' % ( usersgroupid, repo.repo_name ) @@ -928,7 +929,7 @@ class ApiController(JSONRPCController): @HasPermissionAllDecorator('hg.admin') def revoke_users_group_permission(self, apiuser, repoid, usersgroupid): """ - Revoke permission for users group on given repository + Revoke permission for user group on given repository :param apiuser: :param repoid: @@ -943,7 +944,7 @@ class ApiController(JSONRPCController): Session().commit() return dict( - msg='Revoked perm for users group: `%s` in repo: `%s`' % ( + msg='Revoked perm for user group: `%s` in repo: `%s`' % ( users_group.users_group_name, repo.repo_name ), success=True @@ -951,7 +952,7 @@ class ApiController(JSONRPCController): except Exception: log.error(traceback.format_exc()) raise JSONRPCError( - 'failed to edit permission for users group: `%s` in ' + 'failed to edit permission for user group: `%s` in ' 'repo: `%s`' % ( users_group.users_group_name, repo.repo_name ) diff --git a/rhodecode/controllers/changeset.py b/rhodecode/controllers/changeset.py --- a/rhodecode/controllers/changeset.py +++ b/rhodecode/controllers/changeset.py @@ -329,7 +329,7 @@ class ChangesetController(BaseRepoContro text = text or (_('Status change -> %s') % ChangesetStatus.get_status_lbl(status)) - comm = ChangesetCommentsModel().create( + c.co = comm = ChangesetCommentsModel().create( text=text, repo=c.rhodecode_db_repo.repo_id, user=c.rhodecode_user.user_id, @@ -371,12 +371,11 @@ class ChangesetController(BaseRepoContro if not request.environ.get('HTTP_X_PARTIAL_XHR'): return redirect(h.url('changeset_home', repo_name=repo_name, revision=revision)) - + #only ajax below data = { 'target_id': h.safeid(h.safe_unicode(request.POST.get('f_path'))), } if comm: - c.co = comm data.update(comm.get_dict()) data.update({'rendered_text': render('changeset/changeset_comment_block.html')}) diff --git a/rhodecode/controllers/compare.py b/rhodecode/controllers/compare.py --- a/rhodecode/controllers/compare.py +++ b/rhodecode/controllers/compare.py @@ -83,23 +83,28 @@ class CompareController(BaseRepoControll raise HTTPBadRequest() def index(self, org_ref_type, org_ref, other_ref_type, other_ref): - + # org_ref will be evaluated in org_repo org_repo = c.rhodecode_db_repo.repo_name org_ref = (org_ref_type, org_ref) + # other_ref will be evaluated in other_repo other_ref = (other_ref_type, other_ref) other_repo = request.GET.get('other_repo', org_repo) - c.fulldiff = fulldiff = request.GET.get('fulldiff') + # fulldiff disables cut_off_limit + c.fulldiff = request.GET.get('fulldiff') + # only consider this range of changesets rev_start = request.GET.get('rev_start') rev_end = request.GET.get('rev_end') - - c.swap_url = h.url('compare_url', as_form=request.GET.get('as_form'), + # partial uses compare_cs.html template directly + partial = request.environ.get('HTTP_X_PARTIAL_XHR') + # as_form puts hidden input field with changeset revisions + c.as_form = partial and request.GET.get('as_form') + # swap url for compare_diff page - never partial and never as_form + c.swap_url = h.url('compare_url', repo_name=other_repo, org_ref_type=other_ref[0], org_ref=other_ref[1], other_repo=org_repo, other_ref_type=org_ref[0], other_ref=org_ref[1]) - partial = request.environ.get('HTTP_X_PARTIAL_XHR') - org_repo = Repository.get_by_repo_name(org_repo) other_repo = Repository.get_by_repo_name(other_repo) @@ -148,8 +153,6 @@ class CompareController(BaseRepoControll c.statuses = c.rhodecode_db_repo.statuses([x.raw_id for x in c.cs_ranges]) - # defines that we need hidden inputs with changesets - c.as_form = request.GET.get('as_form', False) if partial: return render('compare/compare_cs.html') @@ -163,7 +166,7 @@ class CompareController(BaseRepoControll org_ref = ('rev', ancestor) org_repo = other_repo - diff_limit = self.cut_off_limit if not fulldiff else None + diff_limit = self.cut_off_limit if not c.fulldiff else None _diff = diffs.differ(org_repo, org_ref, other_repo, other_ref) diff --git a/rhodecode/controllers/files.py b/rhodecode/controllers/files.py --- a/rhodecode/controllers/files.py +++ b/rhodecode/controllers/files.py @@ -486,6 +486,8 @@ class FilesController(BaseRepoController c.changeset_1 = c.rhodecode_repo.get_changeset(diff1) try: node1 = c.changeset_1.get_node(f_path) + if node1.is_dir(): + raise NodeError('%s path is a %s not a file' % (node1, type(node1))) except NodeDoesNotExistError: c.changeset_1 = EmptyChangeset(cs=diff1, revision=c.changeset_1.revision, @@ -499,6 +501,7 @@ class FilesController(BaseRepoController c.changeset_2 = c.rhodecode_repo.get_changeset(diff2) try: node2 = c.changeset_2.get_node(f_path) + raise NodeError('%s path is a %s not a file' % (node2, type(node2))) except NodeDoesNotExistError: c.changeset_2 = EmptyChangeset(cs=diff2, revision=c.changeset_2.revision, diff --git a/rhodecode/controllers/home.py b/rhodecode/controllers/home.py --- a/rhodecode/controllers/home.py +++ b/rhodecode/controllers/home.py @@ -81,7 +81,7 @@ class HomeController(BaseController): def branch_tag_switcher(self, repo_name): if request.is_xhr: c.rhodecode_db_repo = Repository.get_by_repo_name(c.repo_name) - c.rhodecode_repo = c.rhodecode_db_repo.scm_instance - return render('/switch_to_list.html') - else: - raise HTTPBadRequest() + if c.rhodecode_db_repo: + c.rhodecode_repo = c.rhodecode_db_repo.scm_instance + return render('/switch_to_list.html') + raise HTTPBadRequest() diff --git a/rhodecode/controllers/pullrequests.py b/rhodecode/controllers/pullrequests.py --- a/rhodecode/controllers/pullrequests.py +++ b/rhodecode/controllers/pullrequests.py @@ -67,29 +67,33 @@ class PullrequestsController(BaseRepoCon c.users_array = repo_model.get_users_js() c.users_groups_array = repo_model.get_users_groups_js() - def _get_repo_refs(self, repo): - hist_l = [] - - branches_group = ([('branch:%s:%s' % (k, v), k) for - k, v in repo.branches.iteritems()], _("Branches")) - bookmarks_group = ([('book:%s:%s' % (k, v), k) for - k, v in repo.bookmarks.iteritems()], _("Bookmarks")) - tags_group = ([('tag:%s:%s' % (k, v), k) for - k, v in repo.tags.iteritems() - if k != 'tip'], _("Tags")) + def _get_repo_refs(self, repo, rev=None): + """return a structure with repo's interesting changesets, suitable for + the selectors in pullrequest.html""" + branches = [('branch:%s:%s' % (k, v), k) + for k, v in repo.branches.iteritems()] + bookmarks = [('book:%s:%s' % (k, v), k) + for k, v in repo.bookmarks.iteritems()] + tags = [('tag:%s:%s' % (k, v), k) + for k, v in repo.tags.iteritems() + if k != 'tip'] tip = repo.tags['tip'] - tipref = 'tag:tip:%s' % tip colontip = ':' + tip - tips = [x[1] for x in branches_group[0] + bookmarks_group[0] + tags_group[0] + tips = [x[1] for x in branches + bookmarks + tags if x[0].endswith(colontip)] - tags_group[0].append((tipref, 'tip (%s)' % ', '.join(tips))) + selected = 'tag:tip:%s' % tip + special = [(selected, 'tip (%s)' % ', '.join(tips))] - hist_l.append(bookmarks_group) - hist_l.append(branches_group) - hist_l.append(tags_group) + if rev: + selected = 'rev:%s:%s' % (rev, rev) + special.append((selected, rev)) - return hist_l, tipref + return [(special, _("Special")), + (bookmarks, _("Bookmarks")), + (branches, _("Branches")), + (tags, _("Tags")), + ], selected def _get_is_allowed_change_status(self, pull_request): owner = self.rhodecode_user.user_id == pull_request.user_id @@ -291,8 +295,6 @@ class PullrequestsController(BaseRepoCon else EmptyChangeset(), 'raw_id')) c.statuses = org_repo.statuses([x.raw_id for x in c.cs_ranges]) - # defines that we need hidden inputs with changesets - c.as_form = request.GET.get('as_form', False) c.org_ref = org_ref[1] c.org_ref_type = org_ref[0] @@ -391,6 +393,7 @@ class PullrequestsController(BaseRepoCon ) c.changeset_statuses = ChangesetStatus.STATUSES + c.as_form = False return render('/pullrequests/pullrequest_show.html') @NotAnonymous() @@ -403,11 +406,15 @@ class PullrequestsController(BaseRepoCon status = request.POST.get('changeset_status') change_status = request.POST.get('change_changeset_status') text = request.POST.get('text') + close_pr = request.POST.get('save_close') allowed_to_change_status = self._get_is_allowed_change_status(pull_request) if status and change_status and allowed_to_change_status: - text = text or (_('Status change -> %s') + _def = (_('status change -> %s') % ChangesetStatus.get_status_lbl(status)) + if close_pr: + _def = _('Closing with') + ' ' + _def + text = text or _def comm = ChangesetCommentsModel().create( text=text, repo=c.rhodecode_db_repo.repo_id, @@ -416,7 +423,9 @@ class PullrequestsController(BaseRepoCon f_path=request.POST.get('f_path'), line_no=request.POST.get('line'), status_change=(ChangesetStatus.get_status_lbl(status) - if status and change_status and allowed_to_change_status else None) + if status and change_status + and allowed_to_change_status else None), + closing_pr=close_pr ) action_logger(self.rhodecode_user, @@ -434,7 +443,7 @@ class PullrequestsController(BaseRepoCon pull_request=pull_request_id ) - if request.POST.get('save_close'): + if close_pr: if status in ['rejected', 'approved']: PullRequestModel().close_pull_request(pull_request_id) action_logger(self.rhodecode_user, diff --git a/rhodecode/lib/auth.py b/rhodecode/lib/auth.py --- a/rhodecode/lib/auth.py +++ b/rhodecode/lib/auth.py @@ -411,7 +411,7 @@ class AuthUser(object): @property def groups_admin(self): """ - Returns list of repositories groups you're an admin of + Returns list of repository groups you're an admin of """ return [x[0] for x in self.permissions['repositories_groups'].iteritems() if x[1] == 'group.admin'] diff --git a/rhodecode/lib/celerylib/__init__.py b/rhodecode/lib/celerylib/__init__.py --- a/rhodecode/lib/celerylib/__init__.py +++ b/rhodecode/lib/celerylib/__init__.py @@ -68,6 +68,8 @@ def run_task(task, *args, **kwargs): except socket.error, e: if isinstance(e, IOError) and e.errno == 111: log.debug('Unable to connect to celeryd. Sync execution') + global CELERY_ON + CELERY_ON = False else: log.error(traceback.format_exc()) except KeyError, e: diff --git a/rhodecode/lib/celerylib/tasks.py b/rhodecode/lib/celerylib/tasks.py --- a/rhodecode/lib/celerylib/tasks.py +++ b/rhodecode/lib/celerylib/tasks.py @@ -251,76 +251,10 @@ def get_commits_stats(repo_name, ts_min_ log.info('LockHeld') return 'Task with key %s already running' % lockkey -@task(ignore_result=True) -@dbsession -def send_password_link(user_email): - from rhodecode.model.notification import EmailNotificationModel - - log = get_logger(send_password_link) - DBS = get_session() - - try: - user = User.get_by_email(user_email) - if user: - log.debug('password reset user found %s' % user) - link = url('reset_password_confirmation', key=user.api_key, - qualified=True) - reg_type = EmailNotificationModel.TYPE_PASSWORD_RESET - body = EmailNotificationModel().get_email_tmpl(reg_type, - **{'user':user.short_contact, - 'reset_url':link}) - log.debug('sending email') - run_task(send_email, user_email, - _("password reset link"), body) - log.info('send new password mail to %s' % user_email) - else: - log.debug("password reset email %s not found" % user_email) - except: - log.error(traceback.format_exc()) - return False - - return True @task(ignore_result=True) @dbsession -def reset_user_password(user_email): - from rhodecode.lib import auth - - log = get_logger(reset_user_password) - DBS = get_session() - - try: - try: - user = User.get_by_email(user_email) - new_passwd = auth.PasswordGenerator().gen_password(8, - auth.PasswordGenerator.ALPHABETS_BIG_SMALL) - if user: - user.password = auth.get_crypt_password(new_passwd) - user.api_key = auth.generate_api_key(user.username) - DBS.add(user) - DBS.commit() - log.info('change password for %s' % user_email) - if new_passwd is None: - raise Exception('unable to generate new password') - except: - log.error(traceback.format_exc()) - DBS.rollback() - - run_task(send_email, user_email, - 'Your new password', - 'Your new RhodeCode password:%s' % (new_passwd)) - log.info('send new password mail to %s' % user_email) - - except: - log.error('Failed to update user password') - log.error(traceback.format_exc()) - - return True - - -@task(ignore_result=True) -@dbsession -def send_email(recipients, subject, body, html_body=''): +def send_email(recipients, subject, body='', html_body=''): """ Sends an email with defined parameters from the .ini files. @@ -348,7 +282,7 @@ def send_email(recipients, subject, body mail_port = email_config.get('smtp_port') tls = str2bool(email_config.get('smtp_use_tls')) ssl = str2bool(email_config.get('smtp_use_ssl')) - debug = str2bool(config.get('debug')) + debug = str2bool(email_config.get('debug')) smtp_auth = email_config.get('smtp_auth') if not mail_server: diff --git a/rhodecode/lib/dbmigrate/schema/db_1_2_0.py b/rhodecode/lib/dbmigrate/schema/db_1_2_0.py --- a/rhodecode/lib/dbmigrate/schema/db_1_2_0.py +++ b/rhodecode/lib/dbmigrate/schema/db_1_2_0.py @@ -41,7 +41,7 @@ from rhodecode.lib.vcs.utils.lazy import from rhodecode.lib.utils2 import str2bool, safe_str, get_changeset_safe, \ generate_api_key, safe_unicode -from rhodecode.lib.exceptions import UsersGroupsAssignedException +from rhodecode.lib.exceptions import UserGroupsAssignedException from rhodecode.lib.compat import json from rhodecode.model.meta import Base, Session @@ -282,7 +282,7 @@ class User(Base, BaseModel): user_followers = relationship('UserFollowing', primaryjoin='UserFollowing.follows_user_id==User.user_id', cascade='all') repo_to_perm = relationship('UserRepoToPerm', primaryjoin='UserRepoToPerm.user_id==User.user_id', cascade='all') - group_member = relationship('UsersGroupMember', cascade='all') + group_member = relationship('UserGroupMember', cascade='all') @property def full_contact(self): @@ -361,7 +361,7 @@ class UserLog(Base, BaseModel): repository = relationship('Repository') -class UsersGroup(Base, BaseModel): +class UserGroup(Base, BaseModel): __tablename__ = 'users_groups' __table_args__ = {'extend_existing':True} @@ -369,7 +369,7 @@ class UsersGroup(Base, BaseModel): users_group_name = Column("users_group_name", String(length=255, convert_unicode=False, assert_unicode=None), nullable=False, unique=True, default=None) users_group_active = Column("users_group_active", Boolean(), nullable=True, unique=None, default=None) - members = relationship('UsersGroupMember', cascade="all, delete, delete-orphan", lazy="joined") + members = relationship('UserGroupMember', cascade="all, delete, delete-orphan", lazy="joined") def __repr__(self): return '' % (self.users_group_name) @@ -425,7 +425,7 @@ class UsersGroup(Base, BaseModel): if v: v = [v] if isinstance(v, basestring) else v for u_id in set(v): - member = UsersGroupMember(users_group_id, u_id) + member = UserGroupMember(users_group_id, u_id) members_list.append(member) setattr(users_group, 'members', members_list) setattr(users_group, k, v) @@ -442,12 +442,12 @@ class UsersGroup(Base, BaseModel): try: # check if this group is not assigned to repo - assigned_groups = UsersGroupRepoToPerm.query()\ - .filter(UsersGroupRepoToPerm.users_group_id == + assigned_groups = UserGroupRepoToPerm.query()\ + .filter(UserGroupRepoToPerm.users_group_id == users_group_id).all() if assigned_groups: - raise UsersGroupsAssignedException('RepoGroup assigned to %s' % + raise UserGroupsAssignedException('RepoGroup assigned to %s' % assigned_groups) users_group = cls.get(users_group_id, cache=False) @@ -458,7 +458,7 @@ class UsersGroup(Base, BaseModel): Session.rollback() raise -class UsersGroupMember(Base, BaseModel): +class UserGroupMember(Base, BaseModel): __tablename__ = 'users_groups_members' __table_args__ = {'extend_existing':True} @@ -467,7 +467,7 @@ class UsersGroupMember(Base, BaseModel): user_id = Column("user_id", Integer(), ForeignKey('users.user_id'), nullable=False, unique=None, default=None) user = relationship('User', lazy='joined') - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') def __init__(self, gr_id='', u_id=''): self.users_group_id = gr_id @@ -475,7 +475,7 @@ class UsersGroupMember(Base, BaseModel): @staticmethod def add_user_to_group(group, user): - ugm = UsersGroupMember() + ugm = UserGroupMember() ugm.users_group = group ugm.user = user Session.add(ugm) @@ -505,7 +505,7 @@ class Repository(Base, BaseModel): fork = relationship('Repository', remote_side=repo_id) group = relationship('RepoGroup') repo_to_perm = relationship('UserRepoToPerm', cascade='all', order_by='UserRepoToPerm.repo_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoToPerm', cascade='all') stats = relationship('Statistics', cascade='all', uselist=False) followers = relationship('UserFollowing', primaryjoin='UserFollowing.follows_repo_id==Repository.repo_id', cascade='all') @@ -909,7 +909,7 @@ class UserToPerm(Base, BaseModel): except: Session.rollback() -class UsersGroupRepoToPerm(Base, BaseModel): +class UserGroupRepoToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_to_perm' __table_args__ = (UniqueConstraint('repository_id', 'users_group_id', 'permission_id'), {'extend_existing':True}) users_group_to_perm_id = Column("users_group_to_perm_id", Integer(), nullable=False, unique=True, default=None, primary_key=True) @@ -917,21 +917,21 @@ class UsersGroupRepoToPerm(Base, BaseMod permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) repository_id = Column("repository_id", Integer(), ForeignKey('repositories.repo_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') repository = relationship('Repository') def __repr__(self): return ' %s >' % (self.users_group, self.repository) -class UsersGroupToPerm(Base, BaseModel): +class UserGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_to_perm' __table_args__ = {'extend_existing':True} users_group_to_perm_id = Column("users_group_to_perm_id", Integer(), nullable=False, unique=True, default=None, primary_key=True) users_group_id = Column("users_group_id", Integer(), ForeignKey('users_groups.users_group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') diff --git a/rhodecode/lib/dbmigrate/schema/db_1_3_0.py b/rhodecode/lib/dbmigrate/schema/db_1_3_0.py --- a/rhodecode/lib/dbmigrate/schema/db_1_3_0.py +++ b/rhodecode/lib/dbmigrate/schema/db_1_3_0.py @@ -305,7 +305,7 @@ class User(Base, BaseModel): repo_to_perm = relationship('UserRepoToPerm', primaryjoin='UserRepoToPerm.user_id==User.user_id', cascade='all') repo_group_to_perm = relationship('UserRepoGroupToPerm', primaryjoin='UserRepoGroupToPerm.user_id==User.user_id', cascade='all') - group_member = relationship('UsersGroupMember', cascade='all') + group_member = relationship('UserGroupMember', cascade='all') notifications = relationship('UserNotification', cascade='all') # notifications assigned to this user @@ -423,7 +423,7 @@ class UserLog(Base, BaseModel): repository = relationship('Repository', cascade='') -class UsersGroup(Base, BaseModel): +class UserGroup(Base, BaseModel): __tablename__ = 'users_groups' __table_args__ = ( {'extend_existing': True, 'mysql_engine':'InnoDB', @@ -434,9 +434,9 @@ class UsersGroup(Base, BaseModel): users_group_name = Column("users_group_name", String(length=255, convert_unicode=False, assert_unicode=None), nullable=False, unique=True, default=None) users_group_active = Column("users_group_active", Boolean(), nullable=True, unique=None, default=None) - members = relationship('UsersGroupMember', cascade="all, delete, delete-orphan", lazy="joined") - users_group_to_perm = relationship('UsersGroupToPerm', cascade='all') - users_group_repo_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + members = relationship('UserGroupMember', cascade="all, delete, delete-orphan", lazy="joined") + users_group_to_perm = relationship('UserGroupToPerm', cascade='all') + users_group_repo_to_perm = relationship('UserGroupRepoToPerm', cascade='all') def __unicode__(self): return u'' % (self.users_group_name) @@ -465,7 +465,7 @@ class UsersGroup(Base, BaseModel): return users_group.get(users_group_id) -class UsersGroupMember(Base, BaseModel): +class UserGroupMember(Base, BaseModel): __tablename__ = 'users_groups_members' __table_args__ = ( {'extend_existing': True, 'mysql_engine':'InnoDB', @@ -477,7 +477,7 @@ class UsersGroupMember(Base, BaseModel): user_id = Column("user_id", Integer(), ForeignKey('users.user_id'), nullable=False, unique=None, default=None) user = relationship('User', lazy='joined') - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') def __init__(self, gr_id='', u_id=''): self.users_group_id = gr_id @@ -510,7 +510,7 @@ class Repository(Base, BaseModel): fork = relationship('Repository', remote_side=repo_id) group = relationship('RepoGroup') repo_to_perm = relationship('UserRepoToPerm', cascade='all', order_by='UserRepoToPerm.repo_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoToPerm', cascade='all') stats = relationship('Statistics', cascade='all', uselist=False) followers = relationship('UserFollowing', primaryjoin='UserFollowing.follows_repo_id==Repository.repo_id', cascade='all') @@ -749,7 +749,7 @@ class RepoGroup(Base, BaseModel): group_description = Column("group_description", String(length=10000, convert_unicode=False, assert_unicode=None), nullable=True, unique=None, default=None) repo_group_to_perm = relationship('UserRepoGroupToPerm', cascade='all', order_by='UserRepoGroupToPerm.group_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoGroupToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoGroupToPerm', cascade='all') parent_group = relationship('RepoGroup', remote_side=group_id) @@ -946,7 +946,7 @@ class UserToPerm(Base, BaseModel): permission = relationship('Permission', lazy='joined') -class UsersGroupRepoToPerm(Base, BaseModel): +class UserGroupRepoToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_to_perm' __table_args__ = ( UniqueConstraint('repository_id', 'users_group_id', 'permission_id'), @@ -958,7 +958,7 @@ class UsersGroupRepoToPerm(Base, BaseMod permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) repository_id = Column("repository_id", Integer(), ForeignKey('repositories.repo_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') repository = relationship('Repository') @@ -975,7 +975,7 @@ class UsersGroupRepoToPerm(Base, BaseMod return u' %s >' % (self.users_group, self.repository) -class UsersGroupToPerm(Base, BaseModel): +class UserGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'permission_id',), @@ -986,7 +986,7 @@ class UsersGroupToPerm(Base, BaseModel): users_group_id = Column("users_group_id", Integer(), ForeignKey('users_groups.users_group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') @@ -1008,7 +1008,7 @@ class UserRepoGroupToPerm(Base, BaseMode permission = relationship('Permission') -class UsersGroupRepoGroupToPerm(Base, BaseModel): +class UserGroupRepoGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'group_id'), @@ -1021,7 +1021,7 @@ class UsersGroupRepoGroupToPerm(Base, Ba group_id = Column("group_id", Integer(), ForeignKey('groups.group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') group = relationship('RepoGroup') diff --git a/rhodecode/lib/dbmigrate/schema/db_1_4_0.py b/rhodecode/lib/dbmigrate/schema/db_1_4_0.py --- a/rhodecode/lib/dbmigrate/schema/db_1_4_0.py +++ b/rhodecode/lib/dbmigrate/schema/db_1_4_0.py @@ -322,7 +322,7 @@ class User(Base, BaseModel): repo_to_perm = relationship('UserRepoToPerm', primaryjoin='UserRepoToPerm.user_id==User.user_id', cascade='all') repo_group_to_perm = relationship('UserRepoGroupToPerm', primaryjoin='UserRepoGroupToPerm.user_id==User.user_id', cascade='all') - group_member = relationship('UsersGroupMember', cascade='all') + group_member = relationship('UserGroupMember', cascade='all') notifications = relationship('UserNotification', cascade='all') # notifications assigned to this user @@ -521,7 +521,7 @@ class UserLog(Base, BaseModel): repository = relationship('Repository', cascade='') -class UsersGroup(Base, BaseModel): +class UserGroup(Base, BaseModel): __tablename__ = 'users_groups' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -533,9 +533,9 @@ class UsersGroup(Base, BaseModel): users_group_active = Column("users_group_active", Boolean(), nullable=True, unique=None, default=None) inherit_default_permissions = Column("users_group_inherit_default_permissions", Boolean(), nullable=False, unique=None, default=True) - members = relationship('UsersGroupMember', cascade="all, delete, delete-orphan", lazy="joined") - users_group_to_perm = relationship('UsersGroupToPerm', cascade='all') - users_group_repo_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + members = relationship('UserGroupMember', cascade="all, delete, delete-orphan", lazy="joined") + users_group_to_perm = relationship('UserGroupToPerm', cascade='all') + users_group_repo_to_perm = relationship('UserGroupRepoToPerm', cascade='all') def __unicode__(self): return u'' % (self.users_group_name) @@ -575,7 +575,7 @@ class UsersGroup(Base, BaseModel): return data -class UsersGroupMember(Base, BaseModel): +class UserGroupMember(Base, BaseModel): __tablename__ = 'users_groups_members' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -587,7 +587,7 @@ class UsersGroupMember(Base, BaseModel): user_id = Column("user_id", Integer(), ForeignKey('users.user_id'), nullable=False, unique=None, default=None) user = relationship('User', lazy='joined') - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') def __init__(self, gr_id='', u_id=''): self.users_group_id = gr_id @@ -625,7 +625,7 @@ class Repository(Base, BaseModel): fork = relationship('Repository', remote_side=repo_id) group = relationship('RepoGroup') repo_to_perm = relationship('UserRepoToPerm', cascade='all', order_by='UserRepoToPerm.repo_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoToPerm', cascade='all') stats = relationship('Statistics', cascade='all', uselist=False) followers = relationship('UserFollowing', @@ -1013,7 +1013,7 @@ class RepoGroup(Base, BaseModel): enable_locking = Column("enable_locking", Boolean(), nullable=False, unique=None, default=False) repo_group_to_perm = relationship('UserRepoGroupToPerm', cascade='all', order_by='UserRepoGroupToPerm.group_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoGroupToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoGroupToPerm', cascade='all') parent_group = relationship('RepoGroup', remote_side=group_id) @@ -1277,7 +1277,7 @@ class UserToPerm(Base, BaseModel): permission = relationship('Permission', lazy='joined') -class UsersGroupRepoToPerm(Base, BaseModel): +class UserGroupRepoToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_to_perm' __table_args__ = ( UniqueConstraint('repository_id', 'users_group_id', 'permission_id'), @@ -1289,7 +1289,7 @@ class UsersGroupRepoToPerm(Base, BaseMod permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) repository_id = Column("repository_id", Integer(), ForeignKey('repositories.repo_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') repository = relationship('Repository') @@ -1306,7 +1306,7 @@ class UsersGroupRepoToPerm(Base, BaseMod return u' %s >' % (self.users_group, self.repository) -class UsersGroupToPerm(Base, BaseModel): +class UserGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'permission_id',), @@ -1317,7 +1317,7 @@ class UsersGroupToPerm(Base, BaseModel): users_group_id = Column("users_group_id", Integer(), ForeignKey('users_groups.users_group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') @@ -1339,7 +1339,7 @@ class UserRepoGroupToPerm(Base, BaseMode permission = relationship('Permission') -class UsersGroupRepoGroupToPerm(Base, BaseModel): +class UserGroupRepoGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'group_id'), @@ -1352,7 +1352,7 @@ class UsersGroupRepoGroupToPerm(Base, Ba group_id = Column("group_id", Integer(), ForeignKey('groups.group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') group = relationship('RepoGroup') diff --git a/rhodecode/lib/dbmigrate/schema/db_1_5_0.py b/rhodecode/lib/dbmigrate/schema/db_1_5_0.py --- a/rhodecode/lib/dbmigrate/schema/db_1_5_0.py +++ b/rhodecode/lib/dbmigrate/schema/db_1_5_0.py @@ -341,7 +341,7 @@ class User(Base, BaseModel): repo_to_perm = relationship('UserRepoToPerm', primaryjoin='UserRepoToPerm.user_id==User.user_id', cascade='all') repo_group_to_perm = relationship('UserRepoGroupToPerm', primaryjoin='UserRepoGroupToPerm.user_id==User.user_id', cascade='all') - group_member = relationship('UsersGroupMember', cascade='all') + group_member = relationship('UserGroupMember', cascade='all') notifications = relationship('UserNotification', cascade='all') # notifications assigned to this user @@ -541,7 +541,7 @@ class UserLog(Base, BaseModel): repository = relationship('Repository', cascade='') -class UsersGroup(Base, BaseModel): +class UserGroup(Base, BaseModel): __tablename__ = 'users_groups' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -553,9 +553,9 @@ class UsersGroup(Base, BaseModel): users_group_active = Column("users_group_active", Boolean(), nullable=True, unique=None, default=None) inherit_default_permissions = Column("users_group_inherit_default_permissions", Boolean(), nullable=False, unique=None, default=True) - members = relationship('UsersGroupMember', cascade="all, delete, delete-orphan", lazy="joined") - users_group_to_perm = relationship('UsersGroupToPerm', cascade='all') - users_group_repo_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + members = relationship('UserGroupMember', cascade="all, delete, delete-orphan", lazy="joined") + users_group_to_perm = relationship('UserGroupToPerm', cascade='all') + users_group_repo_to_perm = relationship('UserGroupRepoToPerm', cascade='all') def __unicode__(self): return u'' % (self.users_group_name) @@ -595,7 +595,7 @@ class UsersGroup(Base, BaseModel): return data -class UsersGroupMember(Base, BaseModel): +class UserGroupMember(Base, BaseModel): __tablename__ = 'users_groups_members' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -607,7 +607,7 @@ class UsersGroupMember(Base, BaseModel): user_id = Column("user_id", Integer(), ForeignKey('users.user_id'), nullable=False, unique=None, default=None) user = relationship('User', lazy='joined') - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') def __init__(self, gr_id='', u_id=''): self.users_group_id = gr_id @@ -645,7 +645,7 @@ class Repository(Base, BaseModel): fork = relationship('Repository', remote_side=repo_id) group = relationship('RepoGroup') repo_to_perm = relationship('UserRepoToPerm', cascade='all', order_by='UserRepoToPerm.repo_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoToPerm', cascade='all') stats = relationship('Statistics', cascade='all', uselist=False) followers = relationship('UserFollowing', @@ -1033,7 +1033,7 @@ class RepoGroup(Base, BaseModel): enable_locking = Column("enable_locking", Boolean(), nullable=False, unique=None, default=False) repo_group_to_perm = relationship('UserRepoGroupToPerm', cascade='all', order_by='UserRepoGroupToPerm.group_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoGroupToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoGroupToPerm', cascade='all') parent_group = relationship('RepoGroup', remote_side=group_id) @@ -1297,7 +1297,7 @@ class UserToPerm(Base, BaseModel): permission = relationship('Permission', lazy='joined') -class UsersGroupRepoToPerm(Base, BaseModel): +class UserGroupRepoToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_to_perm' __table_args__ = ( UniqueConstraint('repository_id', 'users_group_id', 'permission_id'), @@ -1309,7 +1309,7 @@ class UsersGroupRepoToPerm(Base, BaseMod permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) repository_id = Column("repository_id", Integer(), ForeignKey('repositories.repo_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') repository = relationship('Repository') @@ -1326,7 +1326,7 @@ class UsersGroupRepoToPerm(Base, BaseMod return u' %s >' % (self.users_group, self.repository) -class UsersGroupToPerm(Base, BaseModel): +class UserGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'permission_id',), @@ -1337,7 +1337,7 @@ class UsersGroupToPerm(Base, BaseModel): users_group_id = Column("users_group_id", Integer(), ForeignKey('users_groups.users_group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') @@ -1359,7 +1359,7 @@ class UserRepoGroupToPerm(Base, BaseMode permission = relationship('Permission') -class UsersGroupRepoGroupToPerm(Base, BaseModel): +class UserGroupRepoGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'group_id'), @@ -1372,7 +1372,7 @@ class UsersGroupRepoGroupToPerm(Base, Ba group_id = Column("group_id", Integer(), ForeignKey('groups.group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') group = relationship('RepoGroup') diff --git a/rhodecode/lib/dbmigrate/schema/db_1_5_2.py b/rhodecode/lib/dbmigrate/schema/db_1_5_2.py --- a/rhodecode/lib/dbmigrate/schema/db_1_5_2.py +++ b/rhodecode/lib/dbmigrate/schema/db_1_5_2.py @@ -341,7 +341,7 @@ class User(Base, BaseModel): repo_to_perm = relationship('UserRepoToPerm', primaryjoin='UserRepoToPerm.user_id==User.user_id', cascade='all') repo_group_to_perm = relationship('UserRepoGroupToPerm', primaryjoin='UserRepoGroupToPerm.user_id==User.user_id', cascade='all') - group_member = relationship('UsersGroupMember', cascade='all') + group_member = relationship('UserGroupMember', cascade='all') notifications = relationship('UserNotification', cascade='all') # notifications assigned to this user @@ -575,7 +575,7 @@ class UserLog(Base, BaseModel): repository = relationship('Repository', cascade='') -class UsersGroup(Base, BaseModel): +class UserGroup(Base, BaseModel): __tablename__ = 'users_groups' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -587,9 +587,9 @@ class UsersGroup(Base, BaseModel): users_group_active = Column("users_group_active", Boolean(), nullable=True, unique=None, default=None) inherit_default_permissions = Column("users_group_inherit_default_permissions", Boolean(), nullable=False, unique=None, default=True) - members = relationship('UsersGroupMember', cascade="all, delete, delete-orphan", lazy="joined") - users_group_to_perm = relationship('UsersGroupToPerm', cascade='all') - users_group_repo_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + members = relationship('UserGroupMember', cascade="all, delete, delete-orphan", lazy="joined") + users_group_to_perm = relationship('UserGroupToPerm', cascade='all') + users_group_repo_to_perm = relationship('UserGroupRepoToPerm', cascade='all') def __unicode__(self): return u'' % (self.users_group_name) @@ -629,7 +629,7 @@ class UsersGroup(Base, BaseModel): return data -class UsersGroupMember(Base, BaseModel): +class UserGroupMember(Base, BaseModel): __tablename__ = 'users_groups_members' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -641,7 +641,7 @@ class UsersGroupMember(Base, BaseModel): user_id = Column("user_id", Integer(), ForeignKey('users.user_id'), nullable=False, unique=None, default=None) user = relationship('User', lazy='joined') - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') def __init__(self, gr_id='', u_id=''): self.users_group_id = gr_id @@ -680,7 +680,7 @@ class Repository(Base, BaseModel): fork = relationship('Repository', remote_side=repo_id) group = relationship('RepoGroup') repo_to_perm = relationship('UserRepoToPerm', cascade='all', order_by='UserRepoToPerm.repo_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoToPerm', cascade='all') stats = relationship('Statistics', cascade='all', uselist=False) followers = relationship('UserFollowing', @@ -1139,7 +1139,7 @@ class RepoGroup(Base, BaseModel): enable_locking = Column("enable_locking", Boolean(), nullable=False, unique=None, default=False) repo_group_to_perm = relationship('UserRepoGroupToPerm', cascade='all', order_by='UserRepoGroupToPerm.group_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoGroupToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoGroupToPerm', cascade='all') parent_group = relationship('RepoGroup', remote_side=group_id) @@ -1403,7 +1403,7 @@ class UserToPerm(Base, BaseModel): permission = relationship('Permission', lazy='joined') -class UsersGroupRepoToPerm(Base, BaseModel): +class UserGroupRepoToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_to_perm' __table_args__ = ( UniqueConstraint('repository_id', 'users_group_id', 'permission_id'), @@ -1415,7 +1415,7 @@ class UsersGroupRepoToPerm(Base, BaseMod permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) repository_id = Column("repository_id", Integer(), ForeignKey('repositories.repo_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') repository = relationship('Repository') @@ -1432,7 +1432,7 @@ class UsersGroupRepoToPerm(Base, BaseMod return u' %s >' % (self.users_group, self.repository) -class UsersGroupToPerm(Base, BaseModel): +class UserGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'permission_id',), @@ -1443,7 +1443,7 @@ class UsersGroupToPerm(Base, BaseModel): users_group_id = Column("users_group_id", Integer(), ForeignKey('users_groups.users_group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') @@ -1465,7 +1465,7 @@ class UserRepoGroupToPerm(Base, BaseMode permission = relationship('Permission') -class UsersGroupRepoGroupToPerm(Base, BaseModel): +class UserGroupRepoGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'group_id'), @@ -1478,7 +1478,7 @@ class UsersGroupRepoGroupToPerm(Base, Ba group_id = Column("group_id", Integer(), ForeignKey('groups.group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') group = relationship('RepoGroup') diff --git a/rhodecode/lib/dbmigrate/versions/003_version_1_2_0.py b/rhodecode/lib/dbmigrate/versions/003_version_1_2_0.py --- a/rhodecode/lib/dbmigrate/versions/003_version_1_2_0.py +++ b/rhodecode/lib/dbmigrate/versions/003_version_1_2_0.py @@ -34,26 +34,26 @@ def upgrade(migrate_engine): #========================================================================== # Add table `users_groups` #========================================================================== - from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UsersGroup - UsersGroup().__table__.create() + from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UserGroup + UserGroup().__table__.create() #========================================================================== # Add table `users_groups_members` #========================================================================== - from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UsersGroupMember - UsersGroupMember().__table__.create() + from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UserGroupMember + UserGroupMember().__table__.create() #========================================================================== # Add table `users_group_repo_to_perm` #========================================================================== - from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UsersGroupRepoToPerm - UsersGroupRepoToPerm().__table__.create() + from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UserGroupRepoToPerm + UserGroupRepoToPerm().__table__.create() #========================================================================== # Add table `users_group_to_perm` #========================================================================== - from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UsersGroupToPerm - UsersGroupToPerm().__table__.create() + from rhodecode.lib.dbmigrate.schema.db_1_2_0 import UserGroupToPerm + UserGroupToPerm().__table__.create() #========================================================================== # Upgrade of `users` table diff --git a/rhodecode/lib/dbmigrate/versions/004_version_1_3_0.py b/rhodecode/lib/dbmigrate/versions/004_version_1_3_0.py --- a/rhodecode/lib/dbmigrate/versions/004_version_1_3_0.py +++ b/rhodecode/lib/dbmigrate/versions/004_version_1_3_0.py @@ -21,8 +21,8 @@ def upgrade(migrate_engine): #========================================================================== # Add table `users_group_repo_group_to_perm` #========================================================================== - from rhodecode.lib.dbmigrate.schema.db_1_3_0 import UsersGroupRepoGroupToPerm - UsersGroupRepoGroupToPerm().__table__.create() + from rhodecode.lib.dbmigrate.schema.db_1_3_0 import UserGroupRepoGroupToPerm + UserGroupRepoGroupToPerm().__table__.create() #========================================================================== # Add table `changeset_comments` @@ -45,8 +45,8 @@ def upgrade(migrate_engine): #========================================================================== # Add unique to table `users_group_to_perm` #========================================================================== - from rhodecode.lib.dbmigrate.schema.db_1_3_0 import UsersGroupToPerm - tbl = UsersGroupToPerm().__table__ + from rhodecode.lib.dbmigrate.schema.db_1_3_0 import UserGroupToPerm + tbl = UserGroupToPerm().__table__ cons = UniqueConstraint('users_group_id', 'permission_id', table=tbl) cons.create() diff --git a/rhodecode/lib/dbmigrate/versions/006_version_1_4_0.py b/rhodecode/lib/dbmigrate/versions/006_version_1_4_0.py --- a/rhodecode/lib/dbmigrate/versions/006_version_1_4_0.py +++ b/rhodecode/lib/dbmigrate/versions/006_version_1_4_0.py @@ -74,8 +74,8 @@ def upgrade(migrate_engine): #========================================================================== # USERS GROUP TABLE #========================================================================== - from rhodecode.lib.dbmigrate.schema.db_1_3_0 import UsersGroup - tbl = UsersGroup.__table__ + from rhodecode.lib.dbmigrate.schema.db_1_3_0 import UserGroup + tbl = UserGroup.__table__ # add inherit_default_permission column gr_inherit_default_permissions = Column( "users_group_inherit_default_permissions", diff --git a/rhodecode/lib/exceptions.py b/rhodecode/lib/exceptions.py --- a/rhodecode/lib/exceptions.py +++ b/rhodecode/lib/exceptions.py @@ -50,7 +50,7 @@ class UserOwnsReposException(Exception): pass -class UsersGroupsAssignedException(Exception): +class UserGroupsAssignedException(Exception): pass diff --git a/rhodecode/lib/helpers.py b/rhodecode/lib/helpers.py --- a/rhodecode/lib/helpers.py +++ b/rhodecode/lib/helpers.py @@ -684,9 +684,9 @@ def action_parser(user_log, feed=False, get_user_name, 'user_add.png'), 'admin_updated_user': (_('[updated] user'), get_user_name, 'user_edit.png'), - 'admin_created_users_group': (_('[created] users group'), + 'admin_created_users_group': (_('[created] user group'), get_users_group, 'group_add.png'), - 'admin_updated_users_group': (_('[updated] users group'), + 'admin_updated_users_group': (_('[updated] user group'), get_users_group, 'group_edit.png'), 'user_commented_revision': (_('[commented] on revision in repository'), get_cs_links, 'comment_add.png'), @@ -977,7 +977,7 @@ def fancy_file_stats(stats): return literal('
%s%s
' % (width, d_a, d_d)) -def urlify_text(text_): +def urlify_text(text_, safe=True): """ Extrac urls from text and make html links out of them @@ -990,8 +990,10 @@ def urlify_text(text_): def url_func(match_obj): url_full = match_obj.groups()[0] return '%(url)s' % ({'url': url_full}) - - return literal(url_pat.sub(url_func, text_)) + _newtext = url_pat.sub(url_func, text_) + if safe: + return literal(_newtext) + return _newtext def urlify_changesets(text_, repository): @@ -1002,21 +1004,16 @@ def urlify_changesets(text_, repository) :param repository: repo name to build the URL with """ from pylons import url # doh, we need to re-import url to mock it later - URL_PAT = re.compile(r'(?:^|\s)([0-9a-fA-F]{12,40})(?:$|\s)') + URL_PAT = re.compile(r'(^|\s)([0-9a-fA-F]{12,40})($|\s)') def url_func(match_obj): - rev = match_obj.groups()[0] - pref = '' - suf = '' - if match_obj.group().startswith(' '): - pref = ' ' - if match_obj.group().endswith(' '): - suf = ' ' + rev = match_obj.groups()[1] + pref = match_obj.groups()[0] + suf = match_obj.groups()[2] + tmpl = ( '%(pref)s' - '%(rev)s' - '' - '%(suf)s' + '%(rev)s%(suf)s' ) return tmpl % { 'pref': pref, @@ -1062,7 +1059,7 @@ def urlify_commit(text_, repository=None newtext = urlify_changesets(escaper(text_), repository) # extract http/https links and make them real urls - newtext = urlify_text(newtext) + newtext = urlify_text(newtext, safe=False) try: from rhodecode import CONFIG diff --git a/rhodecode/lib/unionrepo.py b/rhodecode/lib/unionrepo.py --- a/rhodecode/lib/unionrepo.py +++ b/rhodecode/lib/unionrepo.py @@ -1,17 +1,20 @@ -# unionrepo.py - repository class for viewing union of repositories +# unionrepo.py - repository class for viewing union of repository changesets # -# Derived from Mercurial 2.5 bundlerepo.py +# Derived from bundlerepo.py # Copyright 2006, 2007 Benoit Boissinot # Copyright 2013 Unity Technologies, Mads Kiilerich # # This software may be used and distributed according to the terms of the # GNU General Public License version 2 or any later version. -"""Repository class for in-memory pull of one local repository to another. +"""Repository class for "in-memory pull" of one local repository to another, +allowing operations like diff and log with revsets. """ +import os from mercurial.node import nullid -from mercurial import util, mdiff +from mercurial.i18n import _ +from mercurial import util, mdiff, cmdutil, scmutil from mercurial import localrepo, changelog, manifest, filelog, revlog class unionrevlog(revlog.revlog): @@ -20,15 +23,14 @@ class unionrevlog(revlog.revlog): # To retrieve a revision, we just need to know the node id so we can # look it up in revlog2. # - # basemap is indexed with revisions coming from the second revlog. - # # To differentiate a rev in the second revlog from a rev in the revlog, - # we check revision against basemap. + # we check revision against repotiprev. + opener = scmutil.readonlyvfs(opener) revlog.revlog.__init__(self, opener, indexfile) self.revlog2 = revlog2 - self.basemap = {} # mapping rev that is in revlog2 to ... nothing n = len(self) + self.repotiprev = n - 1 self.bundlerevs = set() # used by 'bundle()' revset expression for rev2 in self.revlog2: rev = self.revlog2.index[rev2] @@ -42,7 +44,7 @@ class unionrevlog(revlog.revlog): link = linkmapper(linkrev) if node in self.nodemap: - # this happens for for the common revlog revisions + # this happens for the common revlog revisions self.bundlerevs.add(self.nodemap[node]) continue @@ -51,24 +53,23 @@ class unionrevlog(revlog.revlog): e = (None, None, None, None, link, self.rev(p1node), self.rev(p2node), node) - self.basemap[n] = None self.index.insert(-1, e) self.nodemap[node] = n self.bundlerevs.add(n) n += 1 def _chunk(self, rev): - if rev not in self.basemap: + if rev <= self.repotiprev: return revlog.revlog._chunk(self, rev) return self.revlog2._chunk(self.node(rev)) def revdiff(self, rev1, rev2): """return or calculate a delta between two revisions""" - if rev1 in self.basemap and rev2 in self.basemap: + if rev1 > self.repotiprev and rev2 > self.repotiprev: return self.revlog2.revdiff( self.revlog2.rev(self.node(rev1)), self.revlog2.rev(self.node(rev2))) - elif rev1 not in self.basemap and rev2 not in self.basemap: + elif rev1 <= self.repotiprev and rev2 <= self.repotiprev: return revlog.revlog.revdiff(self, rev1, rev2) return mdiff.textdiff(self.revision(self.node(rev1)), @@ -88,7 +89,7 @@ class unionrevlog(revlog.revlog): if node == nullid: return "" - if rev in self.basemap: + if rev > self.repotiprev: text = self.revlog2.revision(node) self._cache = (node, rev, text) else: @@ -144,7 +145,7 @@ class unionrepository(localrepo.localrep util.expandpath(path2)) self.repo2 = localrepo.localrepository(ui, path2) - @util.propertycache + @localrepo.unfilteredpropertycache def changelog(self): return unionchangelog(self.sopener, self.repo2.sopener) @@ -153,7 +154,7 @@ class unionrepository(localrepo.localrep node = self.repo2.changelog.node(rev2) return self.changelog.rev(node) - @util.propertycache + @localrepo.unfilteredpropertycache def manifest(self): return unionmanifest(self.sopener, self.repo2.sopener, self._clrev) @@ -174,8 +175,34 @@ class unionrepository(localrepo.localrep def peer(self): return unionpeer(self) + def getcwd(self): + return os.getcwd() # always outside the repo + def instance(ui, path, create): - u = util.url(path) - assert u.scheme == 'union' - repopath, repopath2 = u.path.split("+", 1) + if create: + raise util.Abort(_('cannot create new union repository')) + parentpath = ui.config("bundle", "mainreporoot", "") + if not parentpath: + # try to find the correct path to the working directory repo + parentpath = cmdutil.findrepo(os.getcwd()) + if parentpath is None: + parentpath = '' + if parentpath: + # Try to make the full path relative so we get a nice, short URL. + # In particular, we don't want temp dir names in test outputs. + cwd = os.getcwd() + if parentpath == cwd: + parentpath = '' + else: + cwd = os.path.join(cwd,'') + if parentpath.startswith(cwd): + parentpath = parentpath[len(cwd):] + if path.startswith('union:'): + s = path.split(":", 1)[1].split("+", 1) + if len(s) == 1: + repopath, repopath2 = parentpath, s[0] + else: + repopath, repopath2 = s + else: + repopath, repopath2 = parentpath, path return unionrepository(ui, repopath, repopath2) diff --git a/rhodecode/lib/vcs/utils/lockfiles.py b/rhodecode/lib/vcs/utils/lockfiles.py --- a/rhodecode/lib/vcs/utils/lockfiles.py +++ b/rhodecode/lib/vcs/utils/lockfiles.py @@ -2,71 +2,71 @@ import os class LockFile(object): - """Provides methods to obtain, check for, and release a file based lock which - should be used to handle concurrent access to the same file. + """Provides methods to obtain, check for, and release a file based lock which + should be used to handle concurrent access to the same file. - As we are a utility class to be derived from, we only use protected methods. + As we are a utility class to be derived from, we only use protected methods. - Locks will automatically be released on destruction""" - __slots__ = ("_file_path", "_owns_lock") + Locks will automatically be released on destruction""" + __slots__ = ("_file_path", "_owns_lock") - def __init__(self, file_path): - self._file_path = file_path - self._owns_lock = False + def __init__(self, file_path): + self._file_path = file_path + self._owns_lock = False - def __del__(self): - self._release_lock() + def __del__(self): + self._release_lock() - def _lock_file_path(self): - """:return: Path to lockfile""" - return "%s.lock" % (self._file_path) + def _lock_file_path(self): + """:return: Path to lockfile""" + return "%s.lock" % (self._file_path) - def _has_lock(self): - """:return: True if we have a lock and if the lockfile still exists - :raise AssertionError: if our lock-file does not exist""" - if not self._owns_lock: - return False + def _has_lock(self): + """:return: True if we have a lock and if the lockfile still exists + :raise AssertionError: if our lock-file does not exist""" + if not self._owns_lock: + return False - return True + return True - def _obtain_lock_or_raise(self): - """Create a lock file as flag for other instances, mark our instance as lock-holder + def _obtain_lock_or_raise(self): + """Create a lock file as flag for other instances, mark our instance as lock-holder - :raise IOError: if a lock was already present or a lock file could not be written""" - if self._has_lock(): - return - lock_file = self._lock_file_path() - if os.path.isfile(lock_file): - raise IOError("Lock for file %r did already exist, delete %r in case the lock is illegal" % (self._file_path, lock_file)) + :raise IOError: if a lock was already present or a lock file could not be written""" + if self._has_lock(): + return + lock_file = self._lock_file_path() + if os.path.isfile(lock_file): + raise IOError("Lock for file %r did already exist, delete %r in case the lock is illegal" % (self._file_path, lock_file)) - try: - fd = os.open(lock_file, os.O_WRONLY | os.O_CREAT | os.O_EXCL, 0) - os.close(fd) - except OSError,e: - raise IOError(str(e)) + try: + fd = os.open(lock_file, os.O_WRONLY | os.O_CREAT | os.O_EXCL, 0) + os.close(fd) + except OSError,e: + raise IOError(str(e)) - self._owns_lock = True + self._owns_lock = True - def _obtain_lock(self): - """The default implementation will raise if a lock cannot be obtained. - Subclasses may override this method to provide a different implementation""" - return self._obtain_lock_or_raise() + def _obtain_lock(self): + """The default implementation will raise if a lock cannot be obtained. + Subclasses may override this method to provide a different implementation""" + return self._obtain_lock_or_raise() - def _release_lock(self): - """Release our lock if we have one""" - if not self._has_lock(): - return + def _release_lock(self): + """Release our lock if we have one""" + if not self._has_lock(): + return - # if someone removed our file beforhand, lets just flag this issue - # instead of failing, to make it more usable. - lfp = self._lock_file_path() - try: - # on bloody windows, the file needs write permissions to be removable. - # Why ... - if os.name == 'nt': - os.chmod(lfp, 0777) - # END handle win32 - os.remove(lfp) - except OSError: - pass - self._owns_lock = False + # if someone removed our file beforhand, lets just flag this issue + # instead of failing, to make it more usable. + lfp = self._lock_file_path() + try: + # on bloody windows, the file needs write permissions to be removable. + # Why ... + if os.name == 'nt': + os.chmod(lfp, 0777) + # END handle win32 + os.remove(lfp) + except OSError: + pass + self._owns_lock = False diff --git a/rhodecode/model/comment.py b/rhodecode/model/comment.py --- a/rhodecode/model/comment.py +++ b/rhodecode/model/comment.py @@ -35,6 +35,7 @@ from rhodecode.model import BaseModel from rhodecode.model.db import ChangesetComment, User, Repository, \ Notification, PullRequest from rhodecode.model.notification import NotificationModel +from rhodecode.model.meta import Session log = logging.getLogger(__name__) @@ -57,8 +58,103 @@ class ChangesetCommentsModel(BaseModel): user_objects.append(user_obj) return user_objects + def _get_notification_data(self, repo, comment, user, comment_text, + line_no=None, revision=None, pull_request=None, + status_change=None, closing_pr=False): + """ + Get notification data + + :param comment_text: + :param line: + :returns: tuple (subj,body,recipients,notification_type,email_kwargs) + """ + # make notification + body = comment_text # text of the comment + line = '' + if line_no: + line = _('on line %s') % line_no + + #changeset + if revision: + notification_type = Notification.TYPE_CHANGESET_COMMENT + cs = repo.scm_instance.get_changeset(revision) + desc = "%s" % (cs.short_id) + + _url = h.url('changeset_home', + repo_name=repo.repo_name, + revision=revision, + anchor='comment-%s' % comment.comment_id, + qualified=True, + ) + subj = safe_unicode( + h.link_to('Re changeset: %(desc)s %(line)s' % \ + {'desc': desc, 'line': line}, + _url) + ) + email_subject = 'User %s commented on changeset %s' % \ + (user.username, h.short_id(revision)) + # get the current participants of this changeset + recipients = ChangesetComment.get_users(revision=revision) + # add changeset author if it's in rhodecode system + cs_author = User.get_from_cs_author(cs.author) + if not cs_author: + #use repo owner if we cannot extract the author correctly + cs_author = repo.user + recipients += [cs_author] + email_kwargs = { + 'status_change': status_change, + 'cs_comment_user': h.person(user.email), + 'cs_target_repo': h.url('summary_home', repo_name=repo.repo_name, + qualified=True), + 'cs_comment_url': _url, + 'raw_id': revision, + 'message': cs.message + } + #pull request + elif pull_request: + notification_type = Notification.TYPE_PULL_REQUEST_COMMENT + desc = comment.pull_request.title + _url = h.url('pullrequest_show', + repo_name=pull_request.other_repo.repo_name, + pull_request_id=pull_request.pull_request_id, + anchor='comment-%s' % comment.comment_id, + qualified=True, + ) + subj = safe_unicode( + h.link_to('Re pull request #%(pr_id)s: %(desc)s %(line)s' % \ + {'desc': desc, + 'pr_id': comment.pull_request.pull_request_id, + 'line': line}, + _url) + ) + email_subject = 'User %s commented on pull request #%s' % \ + (user.username, comment.pull_request.pull_request_id) + # get the current participants of this pull request + recipients = ChangesetComment.get_users(pull_request_id= + pull_request.pull_request_id) + # add pull request author + recipients += [pull_request.author] + + # add the reviewers to notification + recipients += [x.user for x in pull_request.reviewers] + + #set some variables for email notification + email_kwargs = { + 'pr_id': pull_request.pull_request_id, + 'status_change': status_change, + 'closing_pr': closing_pr, + 'pr_comment_url': _url, + 'pr_comment_user': h.person(user.email), + 'pr_target_repo': h.url('summary_home', + repo_name=pull_request.other_repo.repo_name, + qualified=True) + } + + return subj, body, recipients, notification_type, email_kwargs, email_subject + def create(self, text, repo, user, revision=None, pull_request=None, - f_path=None, line_no=None, status_change=None, send_email=True): + f_path=None, line_no=None, status_change=None, closing_pr=False, + send_email=True): """ Creates new comment for changeset or pull request. IF status_change is not none this comment is associated with a @@ -72,9 +168,11 @@ class ChangesetCommentsModel(BaseModel): :param f_path: :param line_no: :param status_change: + :param closing_pr: :param send_email: """ if not text: + log.warning('Missing text for comment, skipping...') return repo = self._get_repo(repo) @@ -87,8 +185,6 @@ class ChangesetCommentsModel(BaseModel): comment.line_no = line_no if revision: - cs = repo.scm_instance.get_changeset(revision) - desc = "%s - %s" % (cs.short_id, h.shorter(cs.message, 256)) comment.revision = revision elif pull_request: pull_request = self.__get_pull_request(pull_request) @@ -96,82 +192,24 @@ class ChangesetCommentsModel(BaseModel): else: raise Exception('Please specify revision or pull_request_id') - self.sa.add(comment) - self.sa.flush() - - # make notification - line = '' - body = text - - #changeset - if revision: - if line_no: - line = _('on line %s') % line_no - subj = safe_unicode( - h.link_to('Re commit: %(desc)s %(line)s' % \ - {'desc': desc, 'line': line}, - h.url('changeset_home', repo_name=repo.repo_name, - revision=revision, - anchor='comment-%s' % comment.comment_id, - qualified=True, - ) - ) - ) - notification_type = Notification.TYPE_CHANGESET_COMMENT - # get the current participants of this changeset - recipients = ChangesetComment.get_users(revision=revision) - # add changeset author if it's in rhodecode system - cs_author = User.get_from_cs_author(cs.author) - if not cs_author: - #use repo owner if we cannot extract the author correctly - cs_author = repo.user - recipients += [cs_author] - email_kwargs = { - 'status_change': status_change, - } - #pull request - elif pull_request: - _url = h.url('pullrequest_show', - repo_name=pull_request.other_repo.repo_name, - pull_request_id=pull_request.pull_request_id, - anchor='comment-%s' % comment.comment_id, - qualified=True, - ) - subj = safe_unicode( - h.link_to('Re pull request #%(pr_id)s: %(desc)s %(line)s' % \ - {'desc': comment.pull_request.title, - 'pr_id': comment.pull_request.pull_request_id, - 'line': line}, - _url) - ) - - notification_type = Notification.TYPE_PULL_REQUEST_COMMENT - # get the current participants of this pull request - recipients = ChangesetComment.get_users(pull_request_id= - pull_request.pull_request_id) - # add pull request author - recipients += [pull_request.author] - - # add the reviewers to notification - recipients += [x.user for x in pull_request.reviewers] - - #set some variables for email notification - email_kwargs = { - 'pr_id': pull_request.pull_request_id, - 'status_change': status_change, - 'pr_comment_url': _url, - 'pr_comment_user': h.person(user.email), - 'pr_target_repo': h.url('summary_home', - repo_name=pull_request.other_repo.repo_name, - qualified=True) - } + Session().add(comment) + Session().flush() if send_email: + (subj, body, recipients, notification_type, + email_kwargs, email_subject) = self._get_notification_data( + repo, comment, user, + comment_text=text, + line_no=line_no, + revision=revision, + pull_request=pull_request, + status_change=status_change, + closing_pr=closing_pr) # create notification objects, and emails NotificationModel().create( created_by=user, subject=subj, body=body, recipients=recipients, type_=notification_type, - email_kwargs=email_kwargs + email_kwargs=email_kwargs, email_subject=email_subject ) mention_recipients = set(self._extract_mentions(body))\ @@ -195,7 +233,7 @@ class ChangesetCommentsModel(BaseModel): :param comment_id: """ comment = self.__get_changeset_comment(comment) - self.sa.delete(comment) + Session().delete(comment) return comment @@ -204,11 +242,8 @@ class ChangesetCommentsModel(BaseModel): Get's main comments based on revision or pull_request_id :param repo_id: - :type repo_id: :param revision: - :type revision: :param pull_request: - :type pull_request: """ q = ChangesetComment.query()\ @@ -226,7 +261,7 @@ class ChangesetCommentsModel(BaseModel): return q.all() def get_inline_comments(self, repo_id, revision=None, pull_request=None): - q = self.sa.query(ChangesetComment)\ + q = Session().query(ChangesetComment)\ .filter(ChangesetComment.repo_id == repo_id)\ .filter(ChangesetComment.line_no != None)\ .filter(ChangesetComment.f_path != None)\ diff --git a/rhodecode/model/db.py b/rhodecode/model/db.py --- a/rhodecode/model/db.py +++ b/rhodecode/model/db.py @@ -44,6 +44,7 @@ from rhodecode.lib.vcs import get_backen from rhodecode.lib.vcs.utils.helpers import get_scm from rhodecode.lib.vcs.exceptions import VCSError from rhodecode.lib.vcs.utils.lazy import LazyProperty +from rhodecode.lib.vcs.backends.base import EmptyChangeset from rhodecode.lib.utils2 import str2bool, safe_str, get_changeset_safe, \ safe_unicode, remove_suffix, remove_prefix @@ -341,7 +342,7 @@ class User(Base, BaseModel): repo_to_perm = relationship('UserRepoToPerm', primaryjoin='UserRepoToPerm.user_id==User.user_id', cascade='all') repo_group_to_perm = relationship('UserRepoGroupToPerm', primaryjoin='UserRepoGroupToPerm.user_id==User.user_id', cascade='all') - group_member = relationship('UsersGroupMember', cascade='all') + group_member = relationship('UserGroupMember', cascade='all') notifications = relationship('UserNotification', cascade='all') # notifications assigned to this user @@ -604,7 +605,7 @@ class UserLog(Base, BaseModel): repository = relationship('Repository', cascade='') -class UsersGroup(Base, BaseModel): +class UserGroup(Base, BaseModel): __tablename__ = 'users_groups' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -616,9 +617,9 @@ class UsersGroup(Base, BaseModel): users_group_active = Column("users_group_active", Boolean(), nullable=True, unique=None, default=None) inherit_default_permissions = Column("users_group_inherit_default_permissions", Boolean(), nullable=False, unique=None, default=True) - members = relationship('UsersGroupMember', cascade="all, delete, delete-orphan", lazy="joined") - users_group_to_perm = relationship('UsersGroupToPerm', cascade='all') - users_group_repo_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + members = relationship('UserGroupMember', cascade="all, delete, delete-orphan", lazy="joined") + users_group_to_perm = relationship('UserGroupToPerm', cascade='all') + users_group_repo_to_perm = relationship('UserGroupRepoToPerm', cascade='all') def __unicode__(self): return u'' % (self.users_group_name) @@ -658,7 +659,7 @@ class UsersGroup(Base, BaseModel): return data -class UsersGroupMember(Base, BaseModel): +class UserGroupMember(Base, BaseModel): __tablename__ = 'users_groups_members' __table_args__ = ( {'extend_existing': True, 'mysql_engine': 'InnoDB', @@ -670,7 +671,7 @@ class UsersGroupMember(Base, BaseModel): user_id = Column("user_id", Integer(), ForeignKey('users.user_id'), nullable=False, unique=None, default=None) user = relationship('User', lazy='joined') - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') def __init__(self, gr_id='', u_id=''): self.users_group_id = gr_id @@ -747,7 +748,7 @@ class Repository(Base, BaseModel): fork = relationship('Repository', remote_side=repo_id) group = relationship('RepoGroup') repo_to_perm = relationship('UserRepoToPerm', cascade='all', order_by='UserRepoToPerm.repo_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoToPerm', cascade='all') stats = relationship('Statistics', cascade='all', uselist=False) followers = relationship('UserFollowing', @@ -1053,15 +1054,18 @@ class Repository(Base, BaseModel): """ from rhodecode.lib.vcs.backends.base import BaseChangeset if cs_cache is None: - cs_cache = self.get_changeset() + cs_cache = EmptyChangeset() + # use no-cache version here + scm_repo = self.scm_instance_no_cache + if scm_repo: + cs_cache = scm_repo.get_changeset() + if isinstance(cs_cache, BaseChangeset): cs_cache = cs_cache.__json__() - if (cs_cache != self.changeset_cache - or not self.last_change - or not self.changeset_cache): + if (cs_cache != self.changeset_cache or not self.changeset_cache): _default = datetime.datetime.fromtimestamp(0) - last_change = cs_cache.get('date') or self.last_change or _default + last_change = cs_cache.get('date') or _default log.debug('updated repo %s with new cs cache %s' % (self, cs_cache)) self.updated_on = last_change self.changeset_cache = cs_cache @@ -1188,7 +1192,8 @@ class Repository(Base, BaseModel): repo_full_path = self.repo_full_path try: alias = get_scm(repo_full_path)[0] - log.debug('Creating instance of %s repository' % alias) + log.debug('Creating instance of %s repository from %s' + % (alias, repo_full_path)) backend = get_backend(alias) except VCSError: log.error(traceback.format_exc()) @@ -1227,7 +1232,7 @@ class RepoGroup(Base, BaseModel): enable_locking = Column("enable_locking", Boolean(), nullable=False, unique=None, default=False) repo_group_to_perm = relationship('UserRepoGroupToPerm', cascade='all', order_by='UserRepoGroupToPerm.group_to_perm_id') - users_group_to_perm = relationship('UsersGroupRepoGroupToPerm', cascade='all') + users_group_to_perm = relationship('UserGroupRepoGroupToPerm', cascade='all') parent_group = relationship('RepoGroup', remote_side=group_id) @@ -1378,10 +1383,10 @@ class Permission(Base, BaseModel): ('repository.write', _('Repository write access')), ('repository.admin', _('Repository admin access')), - ('group.none', _('Repositories Group no access')), - ('group.read', _('Repositories Group read access')), - ('group.write', _('Repositories Group write access')), - ('group.admin', _('Repositories Group admin access')), + ('group.none', _('Repository group no access')), + ('group.read', _('Repository group read access')), + ('group.write', _('Repository group write access')), + ('group.admin', _('Repository group admin access')), ('hg.admin', _('RhodeCode Administrator')), ('hg.create.none', _('Repository creation disabled')), @@ -1490,7 +1495,7 @@ class UserToPerm(Base, BaseModel): permission = relationship('Permission', lazy='joined') -class UsersGroupRepoToPerm(Base, BaseModel): +class UserGroupRepoToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_to_perm' __table_args__ = ( UniqueConstraint('repository_id', 'users_group_id', 'permission_id'), @@ -1502,7 +1507,7 @@ class UsersGroupRepoToPerm(Base, BaseMod permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) repository_id = Column("repository_id", Integer(), ForeignKey('repositories.repo_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') repository = relationship('Repository') @@ -1519,7 +1524,7 @@ class UsersGroupRepoToPerm(Base, BaseMod return u' %s >' % (self.users_group, self.repository) -class UsersGroupToPerm(Base, BaseModel): +class UserGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'permission_id',), @@ -1530,7 +1535,7 @@ class UsersGroupToPerm(Base, BaseModel): users_group_id = Column("users_group_id", Integer(), ForeignKey('users_groups.users_group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') @@ -1552,7 +1557,7 @@ class UserRepoGroupToPerm(Base, BaseMode permission = relationship('Permission') -class UsersGroupRepoGroupToPerm(Base, BaseModel): +class UserGroupRepoGroupToPerm(Base, BaseModel): __tablename__ = 'users_group_repo_group_to_perm' __table_args__ = ( UniqueConstraint('users_group_id', 'group_id'), @@ -1565,7 +1570,7 @@ class UsersGroupRepoGroupToPerm(Base, Ba group_id = Column("group_id", Integer(), ForeignKey('groups.group_id'), nullable=False, unique=None, default=None) permission_id = Column("permission_id", Integer(), ForeignKey('permissions.permission_id'), nullable=False, unique=None, default=None) - users_group = relationship('UsersGroup') + users_group = relationship('UserGroup') permission = relationship('Permission') group = relationship('RepoGroup') diff --git a/rhodecode/model/forms.py b/rhodecode/model/forms.py --- a/rhodecode/model/forms.py +++ b/rhodecode/model/forms.py @@ -94,14 +94,14 @@ def UserForm(edit=False, old_data={}): return _UserForm -def UsersGroupForm(edit=False, old_data={}, available_members=[]): - class _UsersGroupForm(formencode.Schema): +def UserGroupForm(edit=False, old_data={}, available_members=[]): + class _UserGroupForm(formencode.Schema): allow_extra_fields = True filter_extra_fields = True users_group_name = All( v.UnicodeString(strip=True, min=1, not_empty=True), - v.ValidUsersGroup(edit, old_data) + v.ValidUserGroup(edit, old_data) ) users_group_active = v.StringBoolean(if_missing=False) @@ -112,7 +112,7 @@ def UsersGroupForm(edit=False, old_data= if_missing=None, not_empty=False ) - return _UsersGroupForm + return _UserGroupForm def ReposGroupForm(edit=False, old_data={}, available_groups=[], diff --git a/rhodecode/model/notification.py b/rhodecode/model/notification.py --- a/rhodecode/model/notification.py +++ b/rhodecode/model/notification.py @@ -28,12 +28,14 @@ import os import logging import traceback +from pylons import tmpl_context as c from pylons.i18n.translation import _ import rhodecode from rhodecode.lib import helpers as h from rhodecode.model import BaseModel from rhodecode.model.db import Notification, User, UserNotification +from rhodecode.model.meta import Session log = logging.getLogger(__name__) @@ -54,7 +56,7 @@ class NotificationModel(BaseModel): def create(self, created_by, subject, body, recipients=None, type_=Notification.TYPE_MESSAGE, with_email=True, - email_kwargs={}): + email_kwargs={}, email_subject=None): """ Creates notification of given type @@ -68,6 +70,7 @@ class NotificationModel(BaseModel): :param type_: type of notification :param with_email: send email with this notification :param email_kwargs: additional dict to pass as args to email template + :param email_subject: use given subject as email subject """ from rhodecode.lib.celerylib import tasks, run_task @@ -105,9 +108,11 @@ class NotificationModel(BaseModel): # send email with notification to all other participants for rec in rec_objs: - email_subject = NotificationModel().make_description(notif, False) + if not email_subject: + email_subject = NotificationModel()\ + .make_description(notif, show_age=False) type_ = type_ - email_body = body + email_body = None # we set body to none, we just send HTML emails ## this is passed into template kwargs = {'subject': subject, 'body': h.rst_w_mentions(body)} kwargs.update(email_kwargs) @@ -130,7 +135,7 @@ class NotificationModel(BaseModel): .filter(UserNotification.notification == notification)\ .one() - self.sa.delete(obj) + Session().delete(obj) return True except Exception: log.error(traceback.format_exc()) @@ -141,7 +146,6 @@ class NotificationModel(BaseModel): Get mentions for given user, filter them if filter dict is given :param user: - :type user: :param filter: """ user = self._get_user(user) @@ -167,7 +171,7 @@ class NotificationModel(BaseModel): == notification)\ .one() obj.read = True - self.sa.add(obj) + Session().add(obj) return True except Exception: log.error(traceback.format_exc()) @@ -187,7 +191,7 @@ class NotificationModel(BaseModel): # update on joined tables :( for obj in q.all(): obj.read = True - self.sa.add(obj) + Session().add(obj) def get_unread_cnt_for_user(self, user): user = self._get_user(user) @@ -217,7 +221,7 @@ class NotificationModel(BaseModel): #alias _n = notification _map = { - _n.TYPE_CHANGESET_COMMENT: _('commented on commit at %(when)s'), + _n.TYPE_CHANGESET_COMMENT: _('commented on changeset at %(when)s'), _n.TYPE_MESSAGE: _('sent message at %(when)s'), _n.TYPE_MENTION: _('mentioned you at %(when)s'), _n.TYPE_REGISTRATION: _('registered in RhodeCode at %(when)s'), @@ -272,7 +276,8 @@ class EmailNotificationModel(BaseModel): email_template = self._tmpl_lookup.get_template(base) # translator and helpers inject _kwargs = {'_': _, - 'h': h} + 'h': h, + 'c': c} _kwargs.update(kwargs) log.debug('rendering tmpl %s with kwargs %s' % (base, _kwargs)) return email_template.render(**_kwargs) diff --git a/rhodecode/model/pull_request.py b/rhodecode/model/pull_request.py --- a/rhodecode/model/pull_request.py +++ b/rhodecode/model/pull_request.py @@ -75,13 +75,13 @@ class PullRequestModel(BaseModel): new.title = title new.description = description new.author = created_by_user - self.sa.add(new) + Session().add(new) Session().flush() #members for member in set(reviewers): _usr = self._get_user(member) reviewer = PullRequestReviewers(_usr, new) - self.sa.add(reviewer) + Session().add(reviewer) #reset state to under-review ChangesetStatusModel().set_status( @@ -90,7 +90,8 @@ class PullRequestModel(BaseModel): user=created_by_user, pull_request=new ) - + revision_data = [(x.raw_id, x.message) + for x in map(org_repo.get_changeset, revisions)] #notification to reviewers notif = NotificationModel() @@ -114,7 +115,7 @@ class PullRequestModel(BaseModel): 'pr_repo_url': h.url('summary_home', repo_name=other_repo.repo_name, qualified=True,), 'pr_url': pr_url, - 'pr_revisions': revisions + 'pr_revisions': revision_data } notif.create(created_by=created_by_user, subject=subject, body=body, @@ -140,7 +141,7 @@ class PullRequestModel(BaseModel): for uid in to_add: _usr = self._get_user(uid) reviewer = PullRequestReviewers(_usr, pull_request) - self.sa.add(reviewer) + Session().add(reviewer) for uid in to_remove: reviewer = PullRequestReviewers.query()\ @@ -148,7 +149,7 @@ class PullRequestModel(BaseModel): PullRequestReviewers.pull_request==pull_request)\ .scalar() if reviewer: - self.sa.delete(reviewer) + Session().delete(reviewer) def delete(self, pull_request): pull_request = self.__get_pull_request(pull_request) @@ -158,7 +159,7 @@ class PullRequestModel(BaseModel): pull_request = self.__get_pull_request(pull_request) pull_request.status = PullRequest.STATUS_CLOSED pull_request.updated_on = datetime.datetime.now() - self.sa.add(pull_request) + Session().add(pull_request) def _get_changesets(self, alias, org_repo, org_ref, other_repo, other_ref): """ @@ -248,11 +249,7 @@ class PullRequestModel(BaseModel): if len(other_ref) != 2 or not isinstance(org_ref, (list, tuple)): raise Exception('other_ref must be a two element list/tuple') - org_repo_scm = org_repo.scm_instance - other_repo_scm = other_repo.scm_instance - - alias = org_repo.scm_instance.alias - cs_ranges, ancestor = self._get_changesets(alias, - org_repo_scm, org_ref, - other_repo_scm, other_ref) + cs_ranges, ancestor = self._get_changesets(org_repo.scm_instance.alias, + org_repo.scm_instance, org_ref, + other_repo.scm_instance, other_ref) return cs_ranges, ancestor diff --git a/rhodecode/model/repo.py b/rhodecode/model/repo.py --- a/rhodecode/model/repo.py +++ b/rhodecode/model/repo.py @@ -38,7 +38,7 @@ from rhodecode.lib.hooks import log_crea from rhodecode.model import BaseModel from rhodecode.model.db import Repository, UserRepoToPerm, User, Permission, \ - Statistics, UsersGroup, UsersGroupRepoToPerm, RhodeCodeUi, RepoGroup,\ + Statistics, UserGroup, UserGroupRepoToPerm, RhodeCodeUi, RepoGroup,\ RhodeCodeSetting, RepositoryField from rhodecode.lib import helpers as h from rhodecode.lib.auth import HasRepoPermissionAny @@ -54,8 +54,8 @@ class RepoModel(BaseModel): URL_SEPARATOR = Repository.url_sep() def __get_users_group(self, users_group): - return self._get_instance(UsersGroup, users_group, - callback=UsersGroup.get_by_group_name) + return self._get_instance(UserGroup, users_group, + callback=UserGroup.get_by_group_name) def _get_repos_group(self, repos_group): return self._get_instance(RepoGroup, repos_group, @@ -120,8 +120,8 @@ class RepoModel(BaseModel): ) def get_users_groups_js(self): - users_groups = self.sa.query(UsersGroup)\ - .filter(UsersGroup.users_group_active == True).all() + users_groups = self.sa.query(UserGroup)\ + .filter(UserGroup.users_group_active == True).all() return json.dumps([ { @@ -149,11 +149,7 @@ class RepoModel(BaseModel): if not repositories: repositories = Repository.getAll() for repo in repositories: - scm_repo = repo.scm_instance_no_cache - last_cs = EmptyChangeset() - if scm_repo: - last_cs = scm_repo.get_changeset() - repo.update_changeset_cache(last_cs) + repo.update_changeset_cache() def get_repos_as_dict(self, repos_list=None, admin=False, perm_check=True, super_user_actions=False): @@ -415,15 +411,15 @@ class RepoModel(BaseModel): repo = fork_of user_perms = UserRepoToPerm.query()\ .filter(UserRepoToPerm.repository == repo).all() - group_perms = UsersGroupRepoToPerm.query()\ - .filter(UsersGroupRepoToPerm.repository == repo).all() + group_perms = UserGroupRepoToPerm.query()\ + .filter(UserGroupRepoToPerm.repository == repo).all() for perm in user_perms: UserRepoToPerm.create(perm.user, new_repo, perm.permission) for perm in group_perms: - UsersGroupRepoToPerm.create(perm.users_group, new_repo, + UserGroupRepoToPerm.create(perm.users_group, new_repo, perm.permission) else: _create_default_perms() @@ -549,12 +545,12 @@ class RepoModel(BaseModel): def grant_users_group_permission(self, repo, group_name, perm): """ - Grant permission for users group on given repository, or update + Grant permission for user group on given repository, or update existing one if found :param repo: Instance of Repository, repository_id, or repository name :param group_name: Instance of UserGroup, users_group_id, - or users group name + or user group name :param perm: Instance of Permission, or permission_name """ repo = self._get_repo(repo) @@ -562,14 +558,14 @@ class RepoModel(BaseModel): permission = self._get_perm(perm) # check if we have that permission already - obj = self.sa.query(UsersGroupRepoToPerm)\ - .filter(UsersGroupRepoToPerm.users_group == group_name)\ - .filter(UsersGroupRepoToPerm.repository == repo)\ + obj = self.sa.query(UserGroupRepoToPerm)\ + .filter(UserGroupRepoToPerm.users_group == group_name)\ + .filter(UserGroupRepoToPerm.repository == repo)\ .scalar() if obj is None: # create new - obj = UsersGroupRepoToPerm() + obj = UserGroupRepoToPerm() obj.repository = repo obj.users_group = group_name @@ -579,18 +575,18 @@ class RepoModel(BaseModel): def revoke_users_group_permission(self, repo, group_name): """ - Revoke permission for users group on given repository + Revoke permission for user group on given repository :param repo: Instance of Repository, repository_id, or repository name :param group_name: Instance of UserGroup, users_group_id, - or users group name + or user group name """ repo = self._get_repo(repo) group_name = self.__get_users_group(group_name) - obj = self.sa.query(UsersGroupRepoToPerm)\ - .filter(UsersGroupRepoToPerm.repository == repo)\ - .filter(UsersGroupRepoToPerm.users_group == group_name)\ + obj = self.sa.query(UserGroupRepoToPerm)\ + .filter(UserGroupRepoToPerm.repository == repo)\ + .filter(UserGroupRepoToPerm.users_group == group_name)\ .scalar() if obj: self.sa.delete(obj) diff --git a/rhodecode/model/repo_permission.py b/rhodecode/model/repo_permission.py --- a/rhodecode/model/repo_permission.py +++ b/rhodecode/model/repo_permission.py @@ -26,7 +26,7 @@ import logging from rhodecode.model import BaseModel -from rhodecode.model.db import UserRepoToPerm, UsersGroupRepoToPerm, \ +from rhodecode.model.db import UserRepoToPerm, UserGroupRepoToPerm, \ Permission log = logging.getLogger(__name__) @@ -64,9 +64,9 @@ class RepositoryPermissionModel(BaseMode self.sa.delete(current) def get_users_group_permission(self, repository, users_group): - return UsersGroupRepoToPerm.query() \ - .filter(UsersGroupRepoToPerm.users_group == users_group) \ - .filter(UsersGroupRepoToPerm.repository == repository) \ + return UserGroupRepoToPerm.query() \ + .filter(UserGroupRepoToPerm.users_group == users_group) \ + .filter(UserGroupRepoToPerm.repository == repository) \ .scalar() def update_users_group_permission(self, repository, users_group, @@ -77,7 +77,7 @@ class RepositoryPermissionModel(BaseMode if not current.permission is permission: current.permission = permission else: - p = UsersGroupRepoToPerm() + p = UserGroupRepoToPerm() p.users_group = users_group p.repository = repository p.permission = permission diff --git a/rhodecode/model/repos_group.py b/rhodecode/model/repos_group.py --- a/rhodecode/model/repos_group.py +++ b/rhodecode/model/repos_group.py @@ -3,7 +3,7 @@ rhodecode.model.user_group ~~~~~~~~~~~~~~~~~~~~~~~~~~ - users groups model for RhodeCode + repo group model for RhodeCode :created_on: Jan 25, 2011 :author: marcink @@ -33,7 +33,7 @@ from rhodecode.lib.utils2 import LazyPro from rhodecode.model import BaseModel from rhodecode.model.db import RepoGroup, RhodeCodeUi, UserRepoGroupToPerm, \ - User, Permission, UsersGroupRepoGroupToPerm, UsersGroup, Repository + User, Permission, UserGroupRepoGroupToPerm, UserGroup, Repository log = logging.getLogger(__name__) @@ -43,8 +43,8 @@ class ReposGroupModel(BaseModel): cls = RepoGroup def __get_users_group(self, users_group): - return self._get_instance(UsersGroup, users_group, - callback=UsersGroup.get_by_group_name) + return self._get_instance(UserGroup, users_group, + callback=UserGroup.get_by_group_name) def _get_repos_group(self, repos_group): return self._get_instance(RepoGroup, repos_group, @@ -79,7 +79,7 @@ class ReposGroupModel(BaseModel): def __create_group(self, group_name): """ - makes repositories group on filesystem + makes repository group on filesystem :param repo_name: :param parent_id: @@ -218,7 +218,7 @@ class ReposGroupModel(BaseModel): if member_type == 'user': # this updates also current one if found _set_perm_user(obj, user=member, perm=perm) - ## set for users group + ## set for user group else: _set_perm_group(obj, users_group=member, perm=perm) # set new permissions @@ -289,11 +289,11 @@ class ReposGroupModel(BaseModel): def delete_permission(self, repos_group, obj, obj_type, recursive): """ Revokes permission for repos_group for given obj(user or users_group), - obj_type can be user or users group + obj_type can be user or user group :param repos_group: - :param obj: user or users group id - :param obj_type: user or users group type + :param obj: user or user group id + :param obj_type: user or user group type :param recursive: recurse to all children of group """ from rhodecode.model.repo import RepoModel @@ -327,7 +327,7 @@ class ReposGroupModel(BaseModel): def grant_user_permission(self, repos_group, user, perm): """ - Grant permission for user on given repositories group, or update + Grant permission for user on given repository group, or update existing one if found :param repos_group: Instance of ReposGroup, repositories_group_id, @@ -356,7 +356,7 @@ class ReposGroupModel(BaseModel): def revoke_user_permission(self, repos_group, user): """ - Revoke permission for user on given repositories group + Revoke permission for user on given repository group :param repos_group: Instance of ReposGroup, repositories_group_id, or repositories_group name @@ -376,13 +376,13 @@ class ReposGroupModel(BaseModel): def grant_users_group_permission(self, repos_group, group_name, perm): """ - Grant permission for users group on given repositories group, or update + Grant permission for user group on given repository group, or update existing one if found :param repos_group: Instance of ReposGroup, repositories_group_id, or repositories_group name :param group_name: Instance of UserGroup, users_group_id, - or users group name + or user group name :param perm: Instance of Permission, or permission_name """ repos_group = self._get_repos_group(repos_group) @@ -390,14 +390,14 @@ class ReposGroupModel(BaseModel): permission = self._get_perm(perm) # check if we have that permission already - obj = self.sa.query(UsersGroupRepoGroupToPerm)\ - .filter(UsersGroupRepoGroupToPerm.group == repos_group)\ - .filter(UsersGroupRepoGroupToPerm.users_group == group_name)\ + obj = self.sa.query(UserGroupRepoGroupToPerm)\ + .filter(UserGroupRepoGroupToPerm.group == repos_group)\ + .filter(UserGroupRepoGroupToPerm.users_group == group_name)\ .scalar() if obj is None: # create new - obj = UsersGroupRepoGroupToPerm() + obj = UserGroupRepoGroupToPerm() obj.group = repos_group obj.users_group = group_name @@ -407,19 +407,19 @@ class ReposGroupModel(BaseModel): def revoke_users_group_permission(self, repos_group, group_name): """ - Revoke permission for users group on given repositories group + Revoke permission for user group on given repository group :param repos_group: Instance of ReposGroup, repositories_group_id, or repositories_group name :param group_name: Instance of UserGroup, users_group_id, - or users group name + or user group name """ repos_group = self._get_repos_group(repos_group) group_name = self.__get_users_group(group_name) - obj = self.sa.query(UsersGroupRepoGroupToPerm)\ - .filter(UsersGroupRepoGroupToPerm.group == repos_group)\ - .filter(UsersGroupRepoGroupToPerm.users_group == group_name)\ + obj = self.sa.query(UserGroupRepoGroupToPerm)\ + .filter(UserGroupRepoGroupToPerm.group == repos_group)\ + .filter(UserGroupRepoGroupToPerm.users_group == group_name)\ .scalar() if obj: self.sa.delete(obj) diff --git a/rhodecode/model/scm.py b/rhodecode/model/scm.py --- a/rhodecode/model/scm.py +++ b/rhodecode/model/scm.py @@ -291,9 +291,7 @@ class ScmModel(BaseModel): if all_groups is None: all_groups = RepoGroup.query()\ .filter(RepoGroup.group_parent_id == None).all() - group_iter = GroupList(all_groups) - - return group_iter + return [x for x in GroupList(all_groups)] def mark_for_invalidation(self, repo_name): """ diff --git a/rhodecode/model/user.py b/rhodecode/model/user.py --- a/rhodecode/model/user.py +++ b/rhodecode/model/user.py @@ -37,11 +37,12 @@ from rhodecode.lib.utils2 import safe_un from rhodecode.lib.caching_query import FromCache from rhodecode.model import BaseModel from rhodecode.model.db import User, UserRepoToPerm, Repository, Permission, \ - UserToPerm, UsersGroupRepoToPerm, UsersGroupToPerm, UsersGroupMember, \ - Notification, RepoGroup, UserRepoGroupToPerm, UsersGroupRepoGroupToPerm, \ + UserToPerm, UserGroupRepoToPerm, UserGroupToPerm, UserGroupMember, \ + Notification, RepoGroup, UserRepoGroupToPerm, UserGroupRepoGroupToPerm, \ UserEmailMap, UserIpMap from rhodecode.lib.exceptions import DefaultUserException, \ UserOwnsReposException +from rhodecode.model.meta import Session log = logging.getLogger(__name__) @@ -316,11 +317,61 @@ class UserModel(BaseModel): def reset_password_link(self, data): from rhodecode.lib.celerylib import tasks, run_task - run_task(tasks.send_password_link, data['email']) + from rhodecode.model.notification import EmailNotificationModel + user_email = data['email'] + try: + user = User.get_by_email(user_email) + if user: + log.debug('password reset user found %s' % user) + link = url('reset_password_confirmation', key=user.api_key, + qualified=True) + reg_type = EmailNotificationModel.TYPE_PASSWORD_RESET + body = EmailNotificationModel().get_email_tmpl(reg_type, + **{'user': user.short_contact, + 'reset_url': link}) + log.debug('sending email') + run_task(tasks.send_email, user_email, + _("password reset link"), body, body) + log.info('send new password mail to %s' % user_email) + else: + log.debug("password reset email %s not found" % user_email) + except: + log.error(traceback.format_exc()) + return False + + return True def reset_password(self, data): from rhodecode.lib.celerylib import tasks, run_task - run_task(tasks.reset_user_password, data['email']) + from rhodecode.lib import auth + user_email = data['email'] + try: + try: + user = User.get_by_email(user_email) + new_passwd = auth.PasswordGenerator().gen_password(8, + auth.PasswordGenerator.ALPHABETS_BIG_SMALL) + if user: + user.password = auth.get_crypt_password(new_passwd) + user.api_key = auth.generate_api_key(user.username) + Session().add(user) + Session().commit() + log.info('change password for %s' % user_email) + if new_passwd is None: + raise Exception('unable to generate new password') + except: + log.error(traceback.format_exc()) + Session().rollback() + + run_task(tasks.send_email, user_email, + _('Your new password'), + _('Your new RhodeCode password:%s') % (new_passwd)) + log.info('send new password mail to %s' % user_email) + + except: + log.error('Failed to update user password') + log.error(traceback.format_exc()) + + return True def fill_data(self, auth_user, user_id=None, api_key=None): """ @@ -413,7 +464,7 @@ class UserModel(BaseModel): p = 'repository.admin' user.permissions[RK][r_k] = p - # repositories groups + # repository groups for perm in default_repo_groups_perms: rg_k = perm.UserRepoGroupToPerm.group.group_name p = 'group.admin' @@ -446,7 +497,7 @@ class UserModel(BaseModel): user.permissions[RK][r_k] = p - # defaults for repositories groups taken from default user permission + # defaults for repository groups taken from default user permission # on given group for perm in default_repo_groups_perms: rg_k = perm.UserRepoGroupToPerm.group.group_name @@ -461,13 +512,13 @@ class UserModel(BaseModel): 'hg.create.none', 'hg.create.repository']) # USER GROUPS comes first - # users group global permissions - user_perms_from_users_groups = self.sa.query(UsersGroupToPerm)\ - .options(joinedload(UsersGroupToPerm.permission))\ - .join((UsersGroupMember, UsersGroupToPerm.users_group_id == - UsersGroupMember.users_group_id))\ - .filter(UsersGroupMember.user_id == uid)\ - .order_by(UsersGroupToPerm.users_group_id)\ + # user group global permissions + user_perms_from_users_groups = self.sa.query(UserGroupToPerm)\ + .options(joinedload(UserGroupToPerm.permission))\ + .join((UserGroupMember, UserGroupToPerm.users_group_id == + UserGroupMember.users_group_id))\ + .filter(UserGroupMember.user_id == uid)\ + .order_by(UserGroupToPerm.users_group_id)\ .all() #need to group here by groups since user can be in more than one group _grouped = [[x, list(y)] for x, y in @@ -508,21 +559,21 @@ class UserModel(BaseModel): # permission should be selected based on selected method #====================================================================== - # users group for repositories permissions + # user group for repositories permissions user_repo_perms_from_users_groups = \ - self.sa.query(UsersGroupRepoToPerm, Permission, Repository,)\ - .join((Repository, UsersGroupRepoToPerm.repository_id == + self.sa.query(UserGroupRepoToPerm, Permission, Repository,)\ + .join((Repository, UserGroupRepoToPerm.repository_id == Repository.repo_id))\ - .join((Permission, UsersGroupRepoToPerm.permission_id == + .join((Permission, UserGroupRepoToPerm.permission_id == Permission.permission_id))\ - .join((UsersGroupMember, UsersGroupRepoToPerm.users_group_id == - UsersGroupMember.users_group_id))\ - .filter(UsersGroupMember.user_id == uid)\ + .join((UserGroupMember, UserGroupRepoToPerm.users_group_id == + UserGroupMember.users_group_id))\ + .filter(UserGroupMember.user_id == uid)\ .all() multiple_counter = collections.defaultdict(int) for perm in user_repo_perms_from_users_groups: - r_k = perm.UsersGroupRepoToPerm.repository.repo_name + r_k = perm.UserGroupRepoToPerm.repository.repo_name multiple_counter[r_k] += 1 p = perm.Permission.permission_name cur_perm = user.permissions[RK][r_k] @@ -559,27 +610,27 @@ class UserModel(BaseModel): user.permissions[RK][r_k] = p #====================================================================== - # !! PERMISSIONS FOR REPOSITORIES GROUPS !! + # !! PERMISSIONS FOR REPOSITORY GROUPS !! #====================================================================== #====================================================================== # check if user is part of user groups for this repository groups and # fill in his permission from it. _choose_perm decides of which # permission should be selected based on selected method #====================================================================== - # users group for repo groups permissions + # user group for repo groups permissions user_repo_group_perms_from_users_groups = \ - self.sa.query(UsersGroupRepoGroupToPerm, Permission, RepoGroup)\ - .join((RepoGroup, UsersGroupRepoGroupToPerm.group_id == RepoGroup.group_id))\ - .join((Permission, UsersGroupRepoGroupToPerm.permission_id + self.sa.query(UserGroupRepoGroupToPerm, Permission, RepoGroup)\ + .join((RepoGroup, UserGroupRepoGroupToPerm.group_id == RepoGroup.group_id))\ + .join((Permission, UserGroupRepoGroupToPerm.permission_id == Permission.permission_id))\ - .join((UsersGroupMember, UsersGroupRepoGroupToPerm.users_group_id - == UsersGroupMember.users_group_id))\ - .filter(UsersGroupMember.user_id == uid)\ + .join((UserGroupMember, UserGroupRepoGroupToPerm.users_group_id + == UserGroupMember.users_group_id))\ + .filter(UserGroupMember.user_id == uid)\ .all() multiple_counter = collections.defaultdict(int) for perm in user_repo_group_perms_from_users_groups: - g_k = perm.UsersGroupRepoGroupToPerm.group.group_name + g_k = perm.UserGroupRepoGroupToPerm.group.group_name multiple_counter[g_k] += 1 p = perm.Permission.permission_name cur_perm = user.permissions[GK][g_k] diff --git a/rhodecode/model/users_group.py b/rhodecode/model/users_group.py --- a/rhodecode/model/users_group.py +++ b/rhodecode/model/users_group.py @@ -3,7 +3,7 @@ rhodecode.model.users_group ~~~~~~~~~~~~~~~~~~~~~~~~~~~ - users group model for RhodeCode + user group model for RhodeCode :created_on: Oct 1, 2011 :author: nvinot @@ -28,33 +28,33 @@ import logging import traceback from rhodecode.model import BaseModel -from rhodecode.model.db import UsersGroupMember, UsersGroup,\ - UsersGroupRepoToPerm, Permission, UsersGroupToPerm, User -from rhodecode.lib.exceptions import UsersGroupsAssignedException +from rhodecode.model.db import UserGroupMember, UserGroup,\ + UserGroupRepoToPerm, Permission, UserGroupToPerm, User +from rhodecode.lib.exceptions import UserGroupsAssignedException log = logging.getLogger(__name__) -class UsersGroupModel(BaseModel): +class UserGroupModel(BaseModel): - cls = UsersGroup + cls = UserGroup def __get_users_group(self, users_group): - return self._get_instance(UsersGroup, users_group, - callback=UsersGroup.get_by_group_name) + return self._get_instance(UserGroup, users_group, + callback=UserGroup.get_by_group_name) def get(self, users_group_id, cache=False): - return UsersGroup.get(users_group_id) + return UserGroup.get(users_group_id) def get_group(self, users_group): return self.__get_users_group(users_group) def get_by_name(self, name, cache=False, case_insensitive=False): - return UsersGroup.get_by_group_name(name, cache, case_insensitive) + return UserGroup.get_by_group_name(name, cache, case_insensitive) def create(self, name, active=True): try: - new = UsersGroup() + new = UserGroup() new.users_group_name = name new.users_group_active = active self.sa.add(new) @@ -76,7 +76,7 @@ class UsersGroupModel(BaseModel): if v: v = [v] if isinstance(v, basestring) else v for u_id in set(v): - member = UsersGroupMember(users_group.users_group_id, u_id) + member = UserGroupMember(users_group.users_group_id, u_id) members_list.append(member) setattr(users_group, 'members', members_list) setattr(users_group, k, v) @@ -99,11 +99,11 @@ class UsersGroupModel(BaseModel): users_group = self.__get_users_group(users_group) # check if this group is not assigned to repo - assigned_groups = UsersGroupRepoToPerm.query()\ - .filter(UsersGroupRepoToPerm.users_group == users_group).all() + assigned_groups = UserGroupRepoToPerm.query()\ + .filter(UserGroupRepoToPerm.users_group == users_group).all() if assigned_groups and force is False: - raise UsersGroupsAssignedException('RepoGroup assigned to %s' % + raise UserGroupsAssignedException('RepoGroup assigned to %s' % assigned_groups) self.sa.delete(users_group) @@ -121,7 +121,7 @@ class UsersGroupModel(BaseModel): return True try: - users_group_member = UsersGroupMember() + users_group_member = UserGroupMember() users_group_member.user = user users_group_member.users_group = users_group @@ -160,23 +160,23 @@ class UsersGroupModel(BaseModel): users_group = self.__get_users_group(users_group) perm = self._get_perm(perm) - return UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group == users_group)\ - .filter(UsersGroupToPerm.permission == perm).scalar() is not None + return UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group == users_group)\ + .filter(UserGroupToPerm.permission == perm).scalar() is not None def grant_perm(self, users_group, perm): users_group = self.__get_users_group(users_group) perm = self._get_perm(perm) # if this permission is already granted skip it - _perm = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group == users_group)\ - .filter(UsersGroupToPerm.permission == perm)\ + _perm = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group == users_group)\ + .filter(UserGroupToPerm.permission == perm)\ .scalar() if _perm: return - new = UsersGroupToPerm() + new = UserGroupToPerm() new.users_group = users_group new.permission = perm self.sa.add(new) @@ -185,8 +185,8 @@ class UsersGroupModel(BaseModel): users_group = self.__get_users_group(users_group) perm = self._get_perm(perm) - obj = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group == users_group)\ - .filter(UsersGroupToPerm.permission == perm).scalar() + obj = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group == users_group)\ + .filter(UserGroupToPerm.permission == perm).scalar() if obj: self.sa.delete(obj) diff --git a/rhodecode/model/validators.py b/rhodecode/model/validators.py --- a/rhodecode/model/validators.py +++ b/rhodecode/model/validators.py @@ -16,7 +16,7 @@ from formencode.validators import ( from rhodecode.lib.compat import OrderedSet from rhodecode.lib import ipaddr from rhodecode.lib.utils import repo_name_slug -from rhodecode.model.db import RepoGroup, Repository, UsersGroup, User,\ +from rhodecode.model.db import RepoGroup, Repository, UserGroup, User,\ ChangesetStatus from rhodecode.lib.exceptions import LdapImportError from rhodecode.config.routing import ADMIN_PREFIX @@ -129,13 +129,13 @@ def ValidRepoUser(): return _validator -def ValidUsersGroup(edit=False, old_data={}): +def ValidUserGroup(edit=False, old_data={}): class _validator(formencode.validators.FancyValidator): messages = { - 'invalid_group': _(u'Invalid users group name'), - 'group_exist': _(u'Users group "%(usersgroup)s" already exists'), - 'invalid_usersgroup_name': - _(u'users group name may only contain alphanumeric ' + 'invalid_group': _(u'Invalid user group name'), + 'group_exist': _(u'User group "%(usergroup)s" already exists'), + 'invalid_usergroup_name': + _(u'user group name may only contain alphanumeric ' 'characters underscores, periods or dashes and must begin ' 'with alphanumeric character') } @@ -150,19 +150,19 @@ def ValidUsersGroup(edit=False, old_data old_ugname = None if edit: old_id = old_data.get('users_group_id') - old_ugname = UsersGroup.get(old_id).users_group_name + old_ugname = UserGroup.get(old_id).users_group_name if old_ugname != value or not edit: - is_existing_group = UsersGroup.get_by_group_name(value, + is_existing_group = UserGroup.get_by_group_name(value, case_insensitive=True) if is_existing_group: - msg = M(self, 'group_exist', state, usersgroup=value) + msg = M(self, 'group_exist', state, usergroup=value) raise formencode.Invalid(msg, value, state, error_dict=dict(users_group_name=msg) ) if re.match(r'^[a-zA-Z0-9]{1}[a-zA-Z0-9\-\_\.]+$', value) is None: - msg = M(self, 'invalid_usersgroup_name', state) + msg = M(self, 'invalid_usergroup_name', state) raise formencode.Invalid(msg, value, state, error_dict=dict(users_group_name=msg) ) @@ -317,7 +317,7 @@ def ValidRepoName(edit=False, old_data={ _(u'Repository named %(repo)s already exists'), 'repository_in_group_exists': _(u'Repository "%(repo)s" already ' 'exists in group "%(group)s"'), - 'same_group_exists': _(u'Repositories group with name "%(repo)s" ' + 'same_group_exists': _(u'Repository group with name "%(repo)s" ' 'already exists') } @@ -547,7 +547,7 @@ def ValidPerms(type_='repo'): class _validator(formencode.validators.FancyValidator): messages = { 'perm_new_member_name': - _(u'This username or users group name is not valid') + _(u'This username or user group name is not valid') } def to_python(self, value, state): @@ -604,9 +604,9 @@ def ValidPerms(type_='repo'): .filter(User.active == True)\ .filter(User.username == k).one() if t is 'users_group': - self.user_db = UsersGroup.query()\ - .filter(UsersGroup.users_group_active == True)\ - .filter(UsersGroup.users_group_name == k).one() + self.user_db = UserGroup.query()\ + .filter(UserGroup.users_group_active == True)\ + .filter(UserGroup.users_group_name == k).one() except Exception: log.exception('Updated permission failed') diff --git a/rhodecode/public/css/style.css b/rhodecode/public/css/style.css --- a/rhodecode/public/css/style.css +++ b/rhodecode/public/css/style.css @@ -160,56 +160,48 @@ div.options a { .top-left-rounded-corner { -webkit-border-top-left-radius: 8px; -khtml-border-radius-topleft: 8px; - -moz-border-radius-topleft: 8px; border-top-left-radius: 8px; } .top-right-rounded-corner { -webkit-border-top-right-radius: 8px; -khtml-border-radius-topright: 8px; - -moz-border-radius-topright: 8px; border-top-right-radius: 8px; } .bottom-left-rounded-corner { -webkit-border-bottom-left-radius: 8px; -khtml-border-radius-bottomleft: 8px; - -moz-border-radius-bottomleft: 8px; border-bottom-left-radius: 8px; } .bottom-right-rounded-corner { -webkit-border-bottom-right-radius: 8px; -khtml-border-radius-bottomright: 8px; - -moz-border-radius-bottomright: 8px; border-bottom-right-radius: 8px; } .top-left-rounded-corner-mid { -webkit-border-top-left-radius: 4px; -khtml-border-radius-topleft: 4px; - -moz-border-radius-topleft: 4px; border-top-left-radius: 4px; } .top-right-rounded-corner-mid { -webkit-border-top-right-radius: 4px; -khtml-border-radius-topright: 4px; - -moz-border-radius-topright: 4px; border-top-right-radius: 4px; } .bottom-left-rounded-corner-mid { -webkit-border-bottom-left-radius: 4px; -khtml-border-radius-bottomleft: 4px; - -moz-border-radius-bottomleft: 4px; border-bottom-left-radius: 4px; } .bottom-right-rounded-corner-mid { -webkit-border-bottom-right-radius: 4px; -khtml-border-radius-bottomright: 4px; - -moz-border-radius-bottomright: 4px; border-bottom-right-radius: 4px; } @@ -244,12 +236,10 @@ div:hover > a.permalink { #header { } - #header ul#logged-user { margin-bottom: 5px !important; -webkit-border-radius: 0px 0px 8px 8px; -khtml-border-radius: 0px 0px 8px 8px; - -moz-border-radius: 0px 0px 8px 8px; border-radius: 0px 0px 8px 8px; height: 37px; background-color: #003B76; @@ -260,7 +250,7 @@ div:hover > a.permalink { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #003b76), color-stop(100%, #00376e) ); background-image: -webkit-linear-gradient(top, #003b76, #00376e); background-image: -o-linear-gradient(top, #003b76, #00376e); - background-image: linear-gradient(top, #003b76, #00376e); + background-image: linear-gradient(to bottom, #003b76, #00376e); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#003b76',endColorstr='#00376e', GradientType=0 ); box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); } @@ -314,19 +304,18 @@ div:hover > a.permalink { background-color: #003B76; opacity: 0.01; cursor: pointer; - min-height: 10px; + min-height: 10px; width: 100% !important; -webkit-border-radius: 0px 0px 4px 4px; -khtml-border-radius: 0px 0px 4px 4px; - -moz-border-radius: 0px 0px 4px 4px; border-radius: 0px 0px 4px 4px; } #header-dd:hover{ - opacity: 0.2; + opacity: 0.2; -webkit-transition: opacity 0.5s ease-in-out; -moz-transition: opacity 0.5s ease-in-out; - transition: opacity 0.5s ease-in-out; + transition: opacity 0.5s ease-in-out; } #header #header-inner { @@ -341,7 +330,7 @@ div:hover > a.permalink { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #003b76),color-stop(100%, #00376e) ); background-image: -webkit-linear-gradient(top, #003b76, #00376e); background-image: -o-linear-gradient(top, #003b76, #00376e); - background-image: linear-gradient(top, #003b76, #00376e); + background-image: linear-gradient(to bottom, #003b76, #00376e); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#003b76',endColorstr='#00376e', GradientType=0 ); margin: 0; padding: 0; @@ -349,17 +338,15 @@ div:hover > a.permalink { box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); -webkit-border-radius: 0px 0px 4px 4px; -khtml-border-radius: 0px 0px 4px 4px; - -moz-border-radius: 0px 0px 4px 4px; border-radius: 0px 0px 4px 4px; } #header #header-inner.hover { width: 100% !important; -webkit-border-radius: 0px 0px 0px 0px; -khtml-border-radius: 0px 0px 0px 0px; - -moz-border-radius: 0px 0px 0px 0px; border-radius: 0px 0px 0px 0px; position: fixed !important; - z-index: 10000; + z-index: 10000; } .ie7 #header #header-inner.hover, @@ -439,7 +426,6 @@ div:hover > a.permalink { padding: 0; -webkit-border-radius: 4px 4px 4px 4px; -khtml-border-radius: 4px 4px 4px 4px; - -moz-border-radius: 4px 4px 4px 4px; border-radius: 4px 4px 4px 4px; } @@ -1096,7 +1082,6 @@ tbody .yui-dt-editable { cursor: pointer padding: 0 0 10px; -webkit-border-radius: 4px 4px 4px 4px; -khtml-border-radius: 4px 4px 4px 4px; - -moz-border-radius: 4px 4px 4px 4px; border-radius: 4px 4px 4px 4px; box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); } @@ -1126,7 +1111,7 @@ tbody .yui-dt-editable { cursor: pointer background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #003b76), color-stop(100%, #00376e) ); background-image: -webkit-linear-gradient(top, #003b76, #00376e); background-image: -o-linear-gradient(top, #003b76, #00376e); - background-image: linear-gradient(top, #003b76, #00376e); + background-image: linear-gradient(to bottom, #003b76, #00376e); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#003b76', endColorstr='#00376e', GradientType=0 ); margin: 0 0 20px; padding: 0; @@ -1267,7 +1252,7 @@ tbody .yui-dt-editable { cursor: pointer background:-moz-linear-gradient(top,rgba(255,255,255,0),rgba(64,96,128,0.1)); background:-o-linear-gradient(top,rgba(255,255,255,0),rgba(64,96,128,0.1)); background:-ms-linear-gradient(top,rgba(255,255,255,0),rgba(64,96,128,0.1)); - background:linear-gradient(top,rgba(255,255,255,0),rgba(64,96,128,0.1)); + background:linear-gradient(to bottom,rgba(255,255,255,0),rgba(64,96,128,0.1)); display: none; } @@ -1623,7 +1608,6 @@ div.form div.fields div.field div.button padding: 0; border: 1px solid #eee; -webkit-border-radius: 4px; - -moz-border-radius: 4px; border-radius: 4px; } @@ -1949,7 +1933,6 @@ div.form div.fields div.field div.button margin-right: 1px; -webkit-border-radius: 4px 4px 4px 4px; -khtml-border-radius: 4px 4px 4px 4px; - -moz-border-radius: 4px 4px 4px 4px; border-radius: 4px 4px 4px 4px; border: solid 1px #9CF; @@ -2027,12 +2010,11 @@ a.metatag[tag="license"]:hover { background-image : -webkit-gradient( linear, left top, left bottom, color-stop( 0%, #003b76), color-stop( 100%, #00376e)); background-image : -webkit-linear-gradient( top, #003b76, #00376e)); background-image : -o-linear-gradient( top, #003b76, #00376e)); - background-image : linear-gradient( top, #003b76, #00376e); + background-image : linear-gradient(to bottom, #003b76, #00376e); filter :progid : DXImageTransform.Microsoft.gradient ( startColorstr = '#003b76', endColorstr = '#00376e', GradientType = 0); box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); -webkit-border-radius: 4px 4px 4px 4px; -khtml-border-radius: 4px 4px 4px 4px; - -moz-border-radius: 4px 4px 4px 4px; border-radius: 4px 4px 4px 4px; } @@ -2063,7 +2045,7 @@ a.metatag[tag="license"]:hover { background-image : -webkit-gradient( linear, left top, left bottom, color-stop( 0%, #003b76), color-stop( 100%, #00376e)); background-image : -webkit-linear-gradient( top, #003b76, #00376e)); background-image : -o-linear-gradient( top, #003b76, #00376e)); - background-image : linear-gradient( top, #003b76, #00376e); + background-image : linear-gradient(to bottom, #003b76, #00376e); filter : progid : DXImageTransform.Microsoft.gradient ( startColorstr = '#003b76', endColorstr = '#00376e', GradientType = 0); margin: 0 auto; padding: 0; @@ -2147,13 +2129,12 @@ a.metatag[tag="license"]:hover { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #003b76), color-stop(100%, #00376e) ); background-image: -webkit-linear-gradient(top, #003b76, #00376e); background-image: -o-linear-gradient(top, #003b76, #00376e); - background-image: linear-gradient(top, #003b76, #00376e); + background-image: linear-gradient(to bottom, #003b76, #00376e); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#003b76', endColorstr='#00376e', GradientType=0 ); z-index: 999; -webkit-border-radius: 0px 0px 4px 4px; -khtml-border-radius: 0px 0px 4px 4px; - -moz-border-radius: 0px 0px 4px 4px; border-radius: 0px 0px 4px 4px; box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); } @@ -2213,7 +2194,7 @@ a.metatag[tag="license"]:hover { #quick_login .unread a { color: #FFFFFF; display: block; - padding: 2px; + padding: 2px; } #quick_login .notifications a:hover, #quick_login .unread a:hover { @@ -2304,7 +2285,7 @@ a.metatag[tag="license"]:hover { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #003b76), color-stop(100%, #00376e) ); background-image: -webkit-linear-gradient(top, #003b76, #00376e); background-image: -o-linear-gradient(top, #003b76, #00376e); - background-image: linear-gradient(top, #003b76, #00376e); + background-image: linear-gradient(to bottom, #003b76, #00376e); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#003b76', endColorstr='#00376e', GradientType=0 ); margin: 0 auto; @@ -2780,7 +2761,6 @@ h3.files_location { color: #444444; background: #FEA; -webkit-border-radius: 0px 0px 0px 6px; - -moz-border-radius: 0px 0px 0px 6px; border-radius: 0px 0px 0px 6px; padding: 1px; } @@ -2815,7 +2795,6 @@ h3.files_location { text-transform: uppercase; white-space: nowrap; -webkit-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; margin-right: 2px; } @@ -2841,7 +2820,6 @@ h3.files_location { color: #ffffff; white-space: nowrap; -webkit-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; } .right .logtags .branchtag a:hover, .logtags .branchtag a { @@ -2859,7 +2837,6 @@ h3.files_location { color: #ffffff; white-space: nowrap; -webkit-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; } .right .logtags .tagtag a:hover, .logtags .tagtag a { @@ -2878,7 +2855,6 @@ h3.files_location { text-transform: uppercase; white-space: nowrap; -webkit-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; } .right .logbooks .bookbook, .logbooks .bookbook a, .right .logtags .bookbook, .logtags .bookbook a { @@ -2896,7 +2872,6 @@ div.browserblock { line-height: 125%; padding: 0; -webkit-border-radius: 6px 6px 0px 0px; - -moz-border-radius: 6px 6px 0px 0px; border-radius: 6px 6px 0px 0px; } @@ -3109,16 +3084,14 @@ table.code-browser .submodule-dir { border: 2px solid #003367; font: 100% sans-serif; width: auto; - opacity: 1px; + opacity: 1; padding: 8px; white-space: pre-wrap; -webkit-border-radius: 8px 8px 8px 8px; -khtml-border-radius: 8px 8px 8px 8px; - -moz-border-radius: 8px 8px 8px 8px; border-radius: 8px 8px 8px 8px; box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); - -moz-box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); -webkit-box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); } @@ -3130,12 +3103,11 @@ table.code-browser .submodule-dir { border: 2px solid #003367; font: 100% sans-serif; width: auto; - opacity: 1px; + opacity: 1; padding: 8px; white-space: pre-wrap; -webkit-border-radius: 8px 8px 8px 8px; -khtml-border-radius: 8px 8px 8px 8px; - -moz-border-radius: 8px 8px 8px 8px; border-radius: 8px 8px 8px 8px; box-shadow: 0 2px 2px rgba(0, 0, 0, 0.6); } @@ -3182,7 +3154,6 @@ table.code-browser .submodule-dir { position: absolute; width: 100%; background: #000; - -moz-opacity: 0.1px; opacity: .10; filter: alpha(opacity = 10); z-index: 9049; @@ -3428,7 +3399,7 @@ table.code-browser .submodule-dir { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #ee5f5b), color-stop(100%, #c43c35) ); background-image: -webkit-linear-gradient(top, #ee5f5b, #c43c35); background-image: -o-linear-gradient(top, #ee5f5b, #c43c35); - background-image: linear-gradient(top, #ee5f5b, #c43c35); + background-image: linear-gradient(to bottom, #ee5f5b, #c43c35); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ee5f5b',endColorstr='#c43c35', GradientType=0 ); border-color: #c43c35 #c43c35 #882a25; } @@ -3443,7 +3414,7 @@ table.code-browser .submodule-dir { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #fceec1), color-stop(100%, #eedc94) ); background-image: -webkit-linear-gradient(top, #fceec1, #eedc94); background-image: -o-linear-gradient(top, #fceec1, #eedc94); - background-image: linear-gradient(top, #fceec1, #eedc94); + background-image: linear-gradient(to bottom, #fceec1, #eedc94); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fceec1', endColorstr='#eedc94', GradientType=0 ); border-color: #eedc94 #eedc94 #e4c652; } @@ -3457,7 +3428,7 @@ table.code-browser .submodule-dir { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #62c462), color-stop(100%, #57a957) ); background-image: -webkit-linear-gradient(top, #62c462, #57a957); background-image: -o-linear-gradient(top, #62c462, #57a957); - background-image: linear-gradient(top, #62c462, #57a957); + background-image: linear-gradient(to bottom, #62c462, #57a957); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#62c462', endColorstr='#57a957', GradientType=0 ); border-color: #57a957 #57a957 #3d773d; } @@ -3471,7 +3442,7 @@ table.code-browser .submodule-dir { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #5bc0de), color-stop(100%, #339bb9) ); background-image: -webkit-linear-gradient(top, #5bc0de, #339bb9); background-image: -o-linear-gradient(top, #5bc0de, #339bb9); - background-image: linear-gradient(top, #5bc0de, #339bb9); + background-image: linear-gradient(to bottom, #5bc0de, #339bb9); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#5bc0de', endColorstr='#339bb9', GradientType=0 ); border-color: #339bb9 #339bb9 #22697d; } @@ -3492,10 +3463,8 @@ table.code-browser .submodule-dir { border-width: 1px; border-style: solid; -webkit-border-radius: 4px; - -moz-border-radius: 4px; border-radius: 4px; -webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.25); - -moz-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.25); box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.25); } @@ -3524,7 +3493,7 @@ table#permissions_manage { table#permissions_manage span.private_repo_msg { font-size: 0.8em; - opacity: 0.6px; + opacity: 0.6; } table#permissions_manage td.private_repo_msg { @@ -3543,14 +3512,12 @@ div.gravatar { line-height:0; -webkit-border-radius: 3px; -khtml-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; } div.gravatar img { -webkit-border-radius: 2px; -khtml-border-radius: 2px; - -moz-border-radius: 2px; border-radius: 2px; } @@ -3586,7 +3553,7 @@ div.gravatar img { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #F4F4F4),color-stop(100%, #DADADA) ); background-image: -webkit-linear-gradient(top, #F4F4F4, #DADADA) ); background-image: -o-linear-gradient(top, #F4F4F4, #DADADA) ); - background-image: linear-gradient(top, #F4F4F4, #DADADA); + background-image: linear-gradient(to bottom, #F4F4F4, #DADADA); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#F4F4F4', endColorstr='#DADADA', GradientType=0); border-top: 1px solid #DDD; @@ -3598,7 +3565,6 @@ div.gravatar img { margin: 0px 3px 3px 0px; -webkit-border-radius: 4px 4px 4px 4px !important; -khtml-border-radius: 4px 4px 4px 4px !important; - -moz-border-radius: 4px 4px 4px 4px !important; border-radius: 4px 4px 4px 4px !important; cursor: pointer !important; padding: 3px 3px 3px 3px; @@ -3623,7 +3589,6 @@ div.gravatar img { margin: 0px 0px 3px -4px; -webkit-border-radius: 0px 4px 4px 0px !important; -khtml-border-radius: 0px 4px 4px 0px !important; - -moz-border-radius: 0px 4px 4px 0px !important; border-radius: 0px 4px 4px 0px !important; width: 100px; text-align: center; @@ -3642,7 +3607,7 @@ div.gravatar img { } .ui-btn.disabled:hover { - background-position:none; + background-position: 0; color: #999; text-decoration: none; box-shadow: none !important; @@ -3658,7 +3623,7 @@ div.gravatar img { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #ee5f5b), color-stop(100%, #c43c35)); background-image: -webkit-linear-gradient(top, #ee5f5b, #c43c35); background-image: -o-linear-gradient(top, #ee5f5b, #c43c35); - background-image: linear-gradient(top, #ee5f5b, #c43c35); + background-image: linear-gradient(to bottom, #ee5f5b, #c43c35); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ee5f5b', endColorstr='#c43c35', GradientType=0); border-color: #c43c35 #c43c35 #882a25; border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25); @@ -3675,7 +3640,7 @@ div.gravatar img { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #5bc0de), color-stop(100%, #339bb9)); background-image: -webkit-linear-gradient(top, #5bc0de, #339bb9); background-image: -o-linear-gradient(top, #5bc0de, #339bb9); - background-image: linear-gradient(top, #5bc0de, #339bb9); + background-image: linear-gradient(to bottom, #5bc0de, #339bb9); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#5bc0de', endColorstr='#339bb9', GradientType=0); border-color: #339bb9 #339bb9 #22697d; border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25); @@ -3690,7 +3655,7 @@ div.gravatar img { background-image: -webkit-gradient(linear, left top, left bottom, color-stop(0%, #62c462), color-stop(100%, #57a957)); background-image: -webkit-linear-gradient(top, #62c462, #57a957); background-image: -o-linear-gradient(top, #62c462, #57a957); - background-image: linear-gradient(top, #62c462, #57a957); + background-image: linear-gradient(to bottom, #62c462, #57a957); filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#62c462', endColorstr='#57a957', GradientType=0); border-color: #57a957 #57a957 #3d773d; border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25); @@ -3864,7 +3829,6 @@ input.ui-button { padding: 6px 12px; -webkit-border-radius: 4px 4px 4px 4px; -khtml-border-radius: 4px 4px 4px 4px; - -moz-border-radius: 4px 4px 4px 4px; border-radius: 4px 4px 4px 4px; box-shadow: 0 1px 0 #ececec; cursor: pointer; @@ -3996,6 +3960,10 @@ div.form div.fields div.field div.highli padding: 0; } +#login div.form div.fields div.field div.input input.large { + width: 250px; +} + #login div.form div.fields div.field div.checkbox, #register div.form div.fields div.field div.checkbox { margin: 0 0 0 184px; padding: 0; @@ -4038,7 +4006,6 @@ div#legend_container table td, div#legen .q_filter_box { -webkit-box-shadow: rgba(0,0,0,0.07) 0 1px 2px inset; -webkit-border-radius: 4px; - -moz-border-radius: 4px; border-radius: 4px; border: 0 none; color: #AAAAAA; @@ -4188,7 +4155,6 @@ div.readme .readme_box pre { overflow: auto; -webkit-box-shadow: rgba(0,0,0,0.07) 0 1px 2px inset; -webkit-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; } @@ -4290,7 +4256,6 @@ div.rst-block pre { overflow: auto; -webkit-box-shadow: rgba(0,0,0,0.07) 0 1px 2px inset; -webkit-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; } @@ -4304,7 +4269,6 @@ div.rst-block pre { border: 1px solid #ddd; margin-top: 10px; -webkit-border-radius: 4px; - -moz-border-radius: 4px; border-radius: 4px; } @@ -4354,7 +4318,6 @@ div.rst-block pre { .comment-form .clearfix { background: #EEE; -webkit-border-radius: 4px; - -moz-border-radius: 4px; border-radius: 4px; padding: 10px; } @@ -4440,7 +4403,6 @@ form.comment-form { .comment-inline-form .clearfix { background: #EEE; -webkit-border-radius: 4px; - -moz-border-radius: 4px; border-radius: 4px; padding: 5px; } @@ -4517,7 +4479,6 @@ form.comment-inline-form { .inline-comments .comment { border: 1px solid #ddd; -webkit-border-radius: 4px; - -moz-border-radius: 4px; border-radius: 4px; margin: 3px 3px 5px 5px; background-color: #FAFAFA; @@ -4584,7 +4545,6 @@ form.comment-inline-form { background-color: #DEDEDE !important; border-radius: 4px !important; -webkit-border-radius: 4px !important; - -moz-border-radius: 4px !important; } .notification-header { @@ -4609,7 +4569,6 @@ form.comment-inline-form { .notification-table { border: 1px solid #ccc; -webkit-border-radius: 6px 6px 6px 6px; - -moz-border-radius: 6px 6px 6px 6px; border-radius: 6px 6px 6px 6px; clear: both; margin: 0px 20px 0px 20px; @@ -4660,7 +4619,6 @@ PULL REQUESTS text-transform: uppercase; white-space: nowrap; -webkit-border-radius: 3px; - -moz-border-radius: 3px; border-radius: 3px; } @@ -4698,6 +4656,24 @@ PULL REQUESTS /***************************************************************************** DIFFS CSS ******************************************************************************/ +.diff-collapse{ + text-align: center; + margin-bottom: -15px; +} +.diff-collapse-button{ + cursor: pointer; + color: #666; + font-size: 16px; +} +.diff-container { + +} + +.diff-container.hidden{ + display: none; + overflow: hidden; +} + div.diffblock { overflow: auto; @@ -4709,7 +4685,6 @@ div.diffblock { /* new */ line-height: 125%; -webkit-border-radius: 6px 6px 0px 0px; - -moz-border-radius: 6px 6px 0px 0px; border-radius: 6px 6px 0px 0px; } div.diffblock.margined { @@ -4787,12 +4762,13 @@ div.diffblock pre.raw { table.code-difftable { border-collapse: collapse; width: 99%; + border-radius: 0px !important; } table.code-difftable td { padding: 0 !important; background: none !important; border:0 !important; - vertical-align: none !important; + vertical-align: baseline !important } table.code-difftable .context { background:none repeat scroll 0 0 #DDE7EF; @@ -4887,3 +4863,8 @@ table.code-difftable .code pre { div.comment:target>.comment-wrapp { border: solid 2px #ee0 !important; } + +.lineno:target a { + border: solid 2px #ee0 !important; + margin: -2px; +} diff --git a/rhodecode/public/js/rhodecode.js b/rhodecode/public/js/rhodecode.js --- a/rhodecode/public/js/rhodecode.js +++ b/rhodecode/public/js/rhodecode.js @@ -302,12 +302,25 @@ var pyroutes = (function() { } if (matchlist.hasOwnProperty(route_name)) { var route = matchlist[route_name]; + // param substitution for(var i=0; i < route[1].length; i++) { if (!params.hasOwnProperty(route[1][i])) throw new Error(route[1][i] + ' missing in "' + route_name + '" route generation'); } result = sprintf(route[0], params); + + var ret = []; + //extra params => GET + for(param in params){ + if (route[1].indexOf(param) == -1){ + ret.push(encodeURIComponent(param) + "=" + encodeURIComponent(params[param])); + } + } + var _parts = ret.join("&"); + if(_parts){ + result = result +'?'+ _parts + } } return result; @@ -1289,7 +1302,7 @@ var MembersAutoComplete = function (divi return matches; }; - // Define a custom search function for the DataSource of usersGroups + // Define a custom search function for the DataSource of userGroups var matchGroups = function (sQuery) { // Case insensitive matching var query = sQuery.toLowerCase(); @@ -1707,7 +1720,7 @@ var PullRequestAutoComplete = function ( return matches; }; - // Define a custom search function for the DataSource of usersGroups + // Define a custom search function for the DataSource of userGroups var matchGroups = function (sQuery) { // Case insensitive matching var query = sQuery.toLowerCase(); @@ -2149,3 +2162,26 @@ var MultiSelectWidget = function(selecte }); } } + + +// global hooks after DOM is loaded + +YUE.onDOMReady(function(){ + YUE.on(YUQ('.diff-collapse-button'), 'click', function(e){ + var button = e.currentTarget; + var t = YUD.get(button).getAttribute('target'); + console.log(t); + if(YUD.hasClass(t, 'hidden')){ + YUD.removeClass(t, 'hidden'); + YUD.get(button).innerHTML = "↑ {0} ↑".format(_TM['collapse diff']); + } + else if(!YUD.hasClass(t, 'hidden')){ + YUD.addClass(t, 'hidden'); + YUD.get(button).innerHTML = "↓ {0} ↓".format(_TM['expand diff']); + } + }); + + + +}); + diff --git a/rhodecode/templates/admin/notifications/show_notification.html b/rhodecode/templates/admin/notifications/show_notification.html --- a/rhodecode/templates/admin/notifications/show_notification.html +++ b/rhodecode/templates/admin/notifications/show_notification.html @@ -39,7 +39,12 @@ -
${h.rst_w_mentions(c.notification.body)}
+
+
${h.literal(c.notification.subject)}
+ %if c.notification.body: + ${h.rst_w_mentions(c.notification.body)} + %endif +
diff --git a/rhodecode/templates/admin/permissions/permissions.html b/rhodecode/templates/admin/permissions/permissions.html --- a/rhodecode/templates/admin/permissions/permissions.html +++ b/rhodecode/templates/admin/permissions/permissions.html @@ -59,7 +59,7 @@ ${h.checkbox('overwrite_default_group','true')} diff --git a/rhodecode/templates/admin/repos/repo_edit_perms.html b/rhodecode/templates/admin/repos/repo_edit_perms.html --- a/rhodecode/templates/admin/repos/repo_edit_perms.html +++ b/rhodecode/templates/admin/repos/repo_edit_perms.html @@ -38,7 +38,7 @@ %endif %endfor - ## USERS GROUPS + ## USER GROUPS %for g2p in c.repo_info.users_group_to_perm: ${h.radio('g_perm_%s' % g2p.users_group.users_group_name,'repository.none')} @@ -54,7 +54,7 @@ %endif - + ${_('revoke')} @@ -101,7 +101,7 @@ function ajaxActionUser(user_id, field_i var request = YAHOO.util.Connect.asyncRequest('POST', sUrl, callback, postData); }; -function ajaxActionUsersGroup(users_group_id,field_id){ +function ajaxActionUserGroup(users_group_id,field_id){ var sUrl = "${h.url('delete_repo_users_group',repo_name=c.repo_name)}"; var callback = { success:function(o){ @@ -109,7 +109,7 @@ function ajaxActionUsersGroup(users_grou tr.parentNode.removeChild(tr); }, failure:function(o){ - alert("${_('Failed to remove users group')}"); + alert("${_('Failed to remove user group')}"); }, }; var postData = '_method=delete&users_group_id='+users_group_id; diff --git a/rhodecode/templates/admin/repos_groups/repos_group_edit_perms.html b/rhodecode/templates/admin/repos_groups/repos_group_edit_perms.html --- a/rhodecode/templates/admin/repos_groups/repos_group_edit_perms.html +++ b/rhodecode/templates/admin/repos_groups/repos_group_edit_perms.html @@ -40,7 +40,7 @@ %endfor - ## USERS GROUPS + ## USER GROUPS %for g2p in c.repos_group.users_group_to_perm: ${h.radio('g_perm_%s' % g2p.users_group.users_group_name,'group.none')} @@ -51,7 +51,7 @@ ${g2p.users_group.users_group_name} - + ${_('revoke')} @@ -105,7 +105,7 @@ function ajaxActionUser(user_id, field_i var request = YAHOO.util.Connect.asyncRequest('POST', sUrl, callback, postData); }; -function ajaxActionUsersGroup(users_group_id,field_id){ +function ajaxActionUserGroup(users_group_id,field_id){ var sUrl = "${h.url('delete_repos_group_users_group_perm',group_name=c.repos_group.group_name)}"; var callback = { success:function(o){ @@ -113,7 +113,7 @@ function ajaxActionUsersGroup(users_grou tr.parentNode.removeChild(tr); }, failure:function(o){ - alert("${_('Failed to remove users group')}"); + alert("${_('Failed to remove user group')}"); }, }; var recursive = YUD.get('recursive').checked; diff --git a/rhodecode/templates/admin/repos_groups/repos_groups_show.html b/rhodecode/templates/admin/repos_groups/repos_groups_show.html --- a/rhodecode/templates/admin/repos_groups/repos_groups_show.html +++ b/rhodecode/templates/admin/repos_groups/repos_groups_show.html @@ -2,14 +2,14 @@ <%inherit file="/base/base.html"/> <%def name="title()"> - ${_('Repositories groups administration')} - ${c.rhodecode_name} + ${_('Repository groups administration')} - ${c.rhodecode_name} <%def name="breadcrumbs_links()"> ${h.link_to(_('Admin'),h.url('admin_home'))} » - ${_('repositories groups')} + ${_('repository groups')} <%def name="page_nav()"> ${self.menu('admin')} @@ -48,7 +48,7 @@
- ${_('Repositories group')} + ${_('Repository group')} ${h.link_to(h.literal(' » '.join(map(h.safe_unicode,[g.name for g in gr.parents+[gr]]))), url('repos_group_home',group_name=gr.group_name))}
@@ -69,7 +69,7 @@ % else: - ${_('There are no repositories groups yet')} + ${_('There are no repository groups yet')} % endif diff --git a/rhodecode/templates/admin/settings/settings.html b/rhodecode/templates/admin/settings/settings.html --- a/rhodecode/templates/admin/settings/settings.html +++ b/rhodecode/templates/admin/settings/settings.html @@ -64,7 +64,7 @@
${h.checkbox('full_index',True)} - +
@@ -85,7 +85,7 @@
- +
${h.text('rhodecode_title',size=30)} @@ -94,7 +94,7 @@
- +
${h.text('rhodecode_realm',size=30)} @@ -103,7 +103,7 @@
- +
${h.text('rhodecode_ga_code',size=30)} diff --git a/rhodecode/templates/admin/users/user_edit.html b/rhodecode/templates/admin/users/user_edit.html --- a/rhodecode/templates/admin/users/user_edit.html +++ b/rhodecode/templates/admin/users/user_edit.html @@ -40,12 +40,12 @@
- ${c.user.api_key} + ${c.user.api_key}
- ${c.perm_user.ip_addr or "?"} + ${c.perm_user.ip_addr or "?"}
diff --git a/rhodecode/templates/admin/users/user_edit_my_account.html b/rhodecode/templates/admin/users/user_edit_my_account.html --- a/rhodecode/templates/admin/users/user_edit_my_account.html +++ b/rhodecode/templates/admin/users/user_edit_my_account.html @@ -102,6 +102,7 @@
diff --git a/rhodecode/templates/admin/users/user_edit_my_account_pullrequests.html b/rhodecode/templates/admin/users/user_edit_my_account_pullrequests.html --- a/rhodecode/templates/admin/users/user_edit_my_account_pullrequests.html +++ b/rhodecode/templates/admin/users/user_edit_my_account_pullrequests.html @@ -1,4 +1,8 @@ - +%if c.show_closed: + ${h.checkbox('show_closed',checked="checked", label=_('Show closed pull requests'))} +%else: + ${h.checkbox('show_closed',label=_('Show closed pull requests'))} +%endif
${_('Opened by me')}
    %if c.my_pull_requests: diff --git a/rhodecode/templates/admin/users_groups/users_group_add.html b/rhodecode/templates/admin/users_groups/users_group_add.html --- a/rhodecode/templates/admin/users_groups/users_group_add.html +++ b/rhodecode/templates/admin/users_groups/users_group_add.html @@ -2,14 +2,14 @@ <%inherit file="/base/base.html"/> <%def name="title()"> - ${_('Add users group')} - ${c.rhodecode_name} + ${_('Add user group')} - ${c.rhodecode_name} <%def name="breadcrumbs_links()"> ${h.link_to(_('Admin'),h.url('admin_home'))} » - ${h.link_to(_('Users groups'),h.url('users_groups'))} + ${h.link_to(_('User groups'),h.url('users_groups'))} » - ${_('add new users group')} + ${_('add new user group')} <%def name="page_nav()"> diff --git a/rhodecode/templates/admin/users_groups/users_group_edit.html b/rhodecode/templates/admin/users_groups/users_group_edit.html --- a/rhodecode/templates/admin/users_groups/users_group_edit.html +++ b/rhodecode/templates/admin/users_groups/users_group_edit.html @@ -2,13 +2,13 @@ <%inherit file="/base/base.html"/> <%def name="title()"> - ${_('Edit users group')} ${c.users_group.users_group_name} - ${c.rhodecode_name} + ${_('Edit user group')} ${c.users_group.users_group_name} - ${c.rhodecode_name} <%def name="breadcrumbs_links()"> ${h.link_to(_('Admin'),h.url('admin_home'))} » - ${h.link_to(_('UsersGroups'),h.url('users_groups'))} + ${h.link_to(_('UserGroups'),h.url('users_groups'))} » ${_('edit')} "${c.users_group.users_group_name}" diff --git a/rhodecode/templates/admin/users_groups/users_groups.html b/rhodecode/templates/admin/users_groups/users_groups.html --- a/rhodecode/templates/admin/users_groups/users_groups.html +++ b/rhodecode/templates/admin/users_groups/users_groups.html @@ -2,13 +2,13 @@ <%inherit file="/base/base.html"/> <%def name="title()"> - ${_('Users groups administration')} - ${c.rhodecode_name} + ${_('User groups administration')} - ${c.rhodecode_name} <%def name="breadcrumbs_links()"> ${h.link_to(_('Admin'),h.url('admin_home'))} » - ${_('users groups')} + ${_('user groups')} <%def name="page_nav()"> @@ -44,7 +44,7 @@ ${h.form(url('users_group', id=u_group.users_group_id),method='delete')} ${h.submit('remove_',_('delete'),id="remove_group_%s" % u_group.users_group_id, - class_="delete_icon action_button",onclick="return confirm('"+_('Confirm to delete this users group: %s') % u_group.users_group_name+"');")} + class_="delete_icon action_button",onclick="return confirm('"+_('Confirm to delete this user group: %s') % u_group.users_group_name+"');")} ${h.end_form()} diff --git a/rhodecode/templates/base/base.html b/rhodecode/templates/base/base.html old mode 100644 new mode 100755 --- a/rhodecode/templates/base/base.html +++ b/rhodecode/templates/base/base.html @@ -71,9 +71,9 @@
    • ${h.link_to(_('admin journal'),h.url('admin_home'),class_='journal')}
    • ${h.link_to(_('repositories'),h.url('repos'),class_='repos')}
    • -
    • ${h.link_to(_('repositories groups'),h.url('repos_groups'),class_='repos_groups')}
    • +
    • ${h.link_to(_('repository groups'),h.url('repos_groups'),class_='repos_groups')}
    • ${h.link_to(_('users'),h.url('users'),class_='users')}
    • -
    • ${h.link_to(_('users groups'),h.url('users_groups'),class_='groups')}
    • +
    • ${h.link_to(_('user groups'),h.url('users_groups'),class_='groups')}
    • ${h.link_to(_('permissions'),h.url('edit_permission',id='default'),class_='permissions')}
    • ${h.link_to(_('ldap'),h.url('ldap_home'),class_='ldap')}
    • ${h.link_to(_('defaults'),h.url('defaults'),class_='defaults')}
    • @@ -233,7 +233,7 @@
- ${h.text('username',class_='focus',size=40)} + ${h.text('username',class_='focus')}
@@ -242,7 +242,7 @@
- ${h.password('password',class_='focus',size=40)} + ${h.password('password',class_='focus')}
diff --git a/rhodecode/templates/base/root.html b/rhodecode/templates/base/root.html --- a/rhodecode/templates/base/root.html +++ b/rhodecode/templates/base/root.html @@ -52,7 +52,10 @@ 'Open new pull request': "${_('Open new pull request')}", 'Open new pull request for selected changesets': "${_('Open new pull request for selected changesets')}", 'Show selected changes __S -> __E': "${_('Show selected changes __S -> __E')}", + 'Show selected change __S': "${_('Show selected change __S')}", 'Selection link': "${_('Selection link')}", + 'collapse diff': "${_('collapse diff')}", + 'expand diff': "${_('expand diff')}", }; var _TM = TRANSLATION_MAP; diff --git a/rhodecode/templates/branches/branches.html b/rhodecode/templates/branches/branches.html --- a/rhodecode/templates/branches/branches.html +++ b/rhodecode/templates/branches/branches.html @@ -27,7 +27,7 @@ ${self.context_bar('switch-to')}
%if c.repo_branches: - + %endif
<%include file='branches_data.html'/> diff --git a/rhodecode/templates/changelog/changelog.html b/rhodecode/templates/changelog/changelog.html --- a/rhodecode/templates/changelog/changelog.html +++ b/rhodecode/templates/changelog/changelog.html @@ -33,15 +33,15 @@ ${_('%s Changelog') % c.repo_name} - ${c
-
+
@@ -72,7 +72,7 @@ ${_('%s Changelog') % c.repo_name} - ${c
${h.urlify_commit(cs.message, c.repo_name,h.url('changeset_home',repo_name=c.repo_name,revision=cs.raw_id))}
-
↓ ${_('show more')} ↓
+
↓ ${_('Show more')} ↓
@@ -163,7 +163,6 @@ ${_('%s Changelog') % c.repo_name} - ${c if(checked_checkboxes.length>0){ // modify open pull request to show we have selected cs YUD.get('open_new_pr').innerHTML = _TM['Open new pull request for selected changesets']; - }else{ YUD.get('open_new_pr').innerHTML = _TM['Open new pull request']; } @@ -172,32 +171,13 @@ ${_('%s Changelog') % c.repo_name} - ${c if(checked_checkboxes.length>0){ var rev_end = checked_checkboxes[0].name; var rev_start = checked_checkboxes[checked_checkboxes.length-1].name; - - // now select all checkboxes in the middle. - var checked = false; - for (var i=0; i __E']; + var link = (rev_start == rev_end) + ? _TM['Show selected change __S'] + : _TM['Show selected changes __S -> __E']; + link = link.replace('__S',rev_start.substr(0,6)); link = link.replace('__E',rev_end.substr(0,6)); YUD.get('rev_range_container').href = url; diff --git a/rhodecode/templates/changeset/diff_block.html b/rhodecode/templates/changeset/diff_block.html --- a/rhodecode/templates/changeset/diff_block.html +++ b/rhodecode/templates/changeset/diff_block.html @@ -4,7 +4,10 @@ ## ${diff_block.diff_block(change)} ## <%def name="diff_block(change)"> - +
+ ↑ ${_('collapse diff')} ↑ +
+
%for FID,(cs1, cs2, change, path, diff, stats) in change.iteritems(): ##%if op !='removed':
@@ -37,7 +40,7 @@
##%endif %endfor - +
<%def name="diff_block_simple(change)"> @@ -49,8 +52,8 @@
diff --git a/rhodecode/templates/email_templates/changeset_comment.html b/rhodecode/templates/email_templates/changeset_comment.html --- a/rhodecode/templates/email_templates/changeset_comment.html +++ b/rhodecode/templates/email_templates/changeset_comment.html @@ -1,12 +1,17 @@ ## -*- coding: utf-8 -*- <%inherit file="main.html"/> - -

${subject}

- +##message from user goes here +

+${cs_comment_user}:
${body} +

+%if status_change: + ${_('New status')} -> ${status_change} +%endif +
${_('View this comment here')}: ${cs_comment_url}
-% if status_change is not None: -
- ${_('New status')} -> ${status_change} -
-% endif +
+${_('Repo')}: ${cs_target_repo}
+${_('Changeset')}: ${h.short_id(raw_id)}
+${_('desc')}: ${h.shorter(message, 256)}
+
diff --git a/rhodecode/templates/email_templates/password_reset.html b/rhodecode/templates/email_templates/password_reset.html --- a/rhodecode/templates/email_templates/password_reset.html +++ b/rhodecode/templates/email_templates/password_reset.html @@ -1,12 +1,11 @@ ## -*- coding: utf-8 -*- <%inherit file="main.html"/> -${_('Hello')} ${user} - -${_('We received a request to create a new password for your account.')} - -${_('You can generate it by clicking following URL')}: - +

${_('Hello %s') % user}

+
${_('We received a request to create a new password for your account.')}
+
${_('You can generate it by clicking following URL')}:
+
 ${reset_url}
-
-${_("If you didn't request new password please ignore this email.")}
+
+
+${_("If you did not request new password please ignore this email.")} diff --git a/rhodecode/templates/email_templates/pull_request.html b/rhodecode/templates/email_templates/pull_request.html --- a/rhodecode/templates/email_templates/pull_request.html +++ b/rhodecode/templates/email_templates/pull_request.html @@ -10,8 +10,10 @@ ${body}

${_('revisions for reviewing')}
-
    -%for r in pr_revisions: -
  • ${r}
  • +
    +%for r,r_msg in pr_revisions:
    +${h.short_id(r)}:
    +    ${h.shorter(r_msg, 256)}
    +
     %endfor
    -
+ diff --git a/rhodecode/templates/email_templates/pull_request_comment.html b/rhodecode/templates/email_templates/pull_request_comment.html --- a/rhodecode/templates/email_templates/pull_request_comment.html +++ b/rhodecode/templates/email_templates/pull_request_comment.html @@ -1,13 +1,18 @@ ## -*- coding: utf-8 -*- <%inherit file="main.html"/> - -${_('User %s commented on pull request #%s for repository %s') % ('%s' % pr_comment_user, pr_id, pr_target_repo) |n} +${_('Pull request #%s for repository %s') % (pr_id, pr_target_repo) |n} +##message from user goes here +

+${pr_comment_user}:
+${body} +

${_('View this comment here')}: ${pr_comment_url}
-

-${body} - %if status_change: - ${_('New status')} -> ${status_change} + %if closing_pr: + ${_('Closing pull request with status')} -> ${status_change} + %else: + ${_('New status')} -> ${status_change} + %endif %endif

diff --git a/rhodecode/templates/files/files_source.html b/rhodecode/templates/files/files_source.html --- a/rhodecode/templates/files/files_source.html +++ b/rhodecode/templates/files/files_source.html @@ -86,8 +86,11 @@ YUE.onDOMReady(function(){ h_lines.push(parseInt(highlight_ranges[pos])); } } - highlight_lines(h_lines); - + highlight_lines(h_lines); + var _first_line= YUD.get('L'+h_lines[0]); + if(_first_line){ + _first_line.scrollIntoView() + } } // select code link event diff --git a/rhodecode/templates/index_base.html b/rhodecode/templates/index_base.html --- a/rhodecode/templates/index_base.html +++ b/rhodecode/templates/index_base.html @@ -48,7 +48,7 @@
- ${_('Repositories group')} + ${_('Repository group')} ${h.link_to(gr.name,url('repos_group_home',group_name=gr.group_name))}
diff --git a/rhodecode/templates/login.html b/rhodecode/templates/login.html --- a/rhodecode/templates/login.html +++ b/rhodecode/templates/login.html @@ -31,7 +31,7 @@
- ${h.text('username',class_='focus',size=40)} + ${h.text('username',class_='focus large')}
@@ -40,7 +40,7 @@
- ${h.password('password',class_='focus',size=40)} + ${h.password('password',class_='focus large')}
diff --git a/rhodecode/templates/pullrequests/pullrequest.html b/rhodecode/templates/pullrequests/pullrequest.html --- a/rhodecode/templates/pullrequests/pullrequest.html +++ b/rhodecode/templates/pullrequests/pullrequest.html @@ -30,7 +30,7 @@ ${h.select('org_repo','',c.org_repos,class_='refs')}:${h.select('org_ref',c.default_org_ref,c.org_refs,class_='refs')} -
${c.rhodecode_db_repo.description}
+
${c.rhodecode_db_repo.description}
@@ -44,7 +44,7 @@ ${h.select('other_repo',c.default_other_repo,c.other_repos,class_='refs')}:${h.select('other_ref',c.default_other_ref,c.default_other_refs,class_='refs')} -
+
@@ -146,24 +146,25 @@ var select_refs = YUQ('#pull_request_form select.refs') var rev_data = { - 'org_repo': org_repo, - 'org_ref': org_ref[1], - 'org_ref_type': org_ref[0], - 'other_repo': other_repo, - 'other_ref': other_ref[1], - 'other_ref_type': other_ref[0], + 'org_repo': org_repo, + 'org_ref': org_ref[2], + 'org_ref_type': 'rev', + 'other_repo': other_repo, + 'other_ref': other_ref[2], + 'other_ref_type': 'rev', }; // gather the org/other ref and repo here for (k in rev_data){ - url = url.replace('__'+k+'__',rev_data[k]); + url = url.replace('__'+k+'__',rev_data[k]); } + YUD.get('pull_request_overview').innerHTML = "${_('Loading ...')}"; + YUD.get('pull_request_overview_url').href = url; // shouldn't have as_form ... but ... + YUD.setStyle(YUD.get('pull_request_overview_url').parentElement,'display',''); ypjax(url,'pull_request_overview', function(data){ var sel_box = YUQ('#pull_request_form #other_repo')[0]; var repo_name = sel_box.options[sel_box.selectedIndex].value; var _data = other_repos_info[repo_name]; - YUD.get('pull_request_overview_url').href = url; - YUD.setStyle(YUD.get('pull_request_overview_url').parentElement,'display',''); YUD.get('other_repo_desc').innerHTML = other_repos_info[repo_name]['description']; YUD.get('other_ref').innerHTML = other_repos_info[repo_name]['revs']; // select back the revision that was just compared @@ -171,8 +172,8 @@ // reset && add the reviewer based on selected repo YUD.get('review_members').innerHTML = ''; addReviewMember(_data.user.user_id, _data.user.firstname, - _data.user.lastname, _data.user.username, - _data.user.gravatar_link); + _data.user.lastname, _data.user.username, + _data.user.gravatar_link); }) } diff --git a/rhodecode/templates/pullrequests/pullrequest_show.html b/rhodecode/templates/pullrequests/pullrequest_show.html --- a/rhodecode/templates/pullrequests/pullrequest_show.html +++ b/rhodecode/templates/pullrequests/pullrequest_show.html @@ -7,7 +7,7 @@ <%def name="breadcrumbs_links()"> ${h.link_to(_(u'Home'),h.url('/'))} » - ${h.link_to(c.repo_name,h.url('changelog_home',repo_name=c.repo_name))} + ${h.repo_link(c.rhodecode_db_repo.groups_and_repo)} » ${_('Pull request #%s') % c.pull_request.pull_request_id} @@ -22,7 +22,12 @@ %if c.pull_request.is_closed():
${_('Closed %s') % (h.age(c.pull_request.updated_on))} ${_('with status %s') % h.changeset_status_lbl(c.current_changeset_status)}
%endif -

${_('Title')}: ${c.pull_request.title}

+

+ %if c.pull_request.is_closed(): + + %endif + + ${_('Title')}: ${c.pull_request.title}

diff --git a/rhodecode/templates/switch_to_list.html b/rhodecode/templates/switch_to_list.html --- a/rhodecode/templates/switch_to_list.html +++ b/rhodecode/templates/switch_to_list.html @@ -4,7 +4,7 @@
    %if c.rhodecode_repo.branches.values(): %for cnt,branch in enumerate(c.rhodecode_repo.branches.items()): -
  • ${h.link_to('%s - %s' % (branch[0],h.short_id(branch[1])),h.url('files_home',repo_name=c.repo_name,revision=branch[0]))}
  • +
  • ${h.link_to('%s - %s' % (branch[0],h.short_id(branch[1])),h.url('files_home',repo_name=c.repo_name,revision=(branch[0] if '/' not in branch[0] else branch[1]), at=branch[0]))}
  • %endfor %else:
  • ${h.link_to(_('There are no branches yet'),'#')}
  • @@ -16,7 +16,7 @@
      %if c.rhodecode_repo.tags.values(): %for cnt,tag in enumerate(c.rhodecode_repo.tags.items()): -
    • ${h.link_to('%s - %s' % (tag[0],h.short_id(tag[1])),h.url('files_home',repo_name=c.repo_name,revision=tag[0]))}
    • +
    • ${h.link_to('%s - %s' % (tag[0],h.short_id(tag[1])),h.url('files_home',repo_name=c.repo_name,revision=(tag[0] if '/' not in tag[0] else tag[1]), at=tag[0]))}
    • %endfor %else:
    • ${h.link_to(_('There are no tags yet'),'#')}
    • @@ -29,7 +29,7 @@
        %if c.rhodecode_repo.bookmarks.values(): %for cnt,book in enumerate(c.rhodecode_repo.bookmarks.items()): -
      • ${h.link_to('%s - %s' % (book[0],h.short_id(book[1])),h.url('files_home',repo_name=c.repo_name,revision=book[1]))}
      • +
      • ${h.link_to('%s - %s' % (book[0],h.short_id(book[1])),h.url('files_home',repo_name=c.repo_name,revision=(book[0] if '/' not in book[0] else book[1]), at=book[0]))}
      • %endfor %else:
      • ${h.link_to(_('There are no bookmarks yet'),'#')}
      • diff --git a/rhodecode/templates/tags/tags.html b/rhodecode/templates/tags/tags.html --- a/rhodecode/templates/tags/tags.html +++ b/rhodecode/templates/tags/tags.html @@ -27,7 +27,7 @@ ${self.context_bar('switch-to')}
%if c.repo_tags: - + %endif
<%include file='tags_data.html'/> diff --git a/rhodecode/tests/api/api_base.py b/rhodecode/tests/api/api_base.py --- a/rhodecode/tests/api/api_base.py +++ b/rhodecode/tests/api/api_base.py @@ -6,7 +6,7 @@ from rhodecode.tests import * from rhodecode.lib.compat import json from rhodecode.lib.auth import AuthUser from rhodecode.model.user import UserModel -from rhodecode.model.users_group import UsersGroupModel +from rhodecode.model.users_group import UserGroupModel from rhodecode.model.repo import RepoModel from rhodecode.model.meta import Session from rhodecode.model.scm import ScmModel @@ -43,19 +43,19 @@ def api_call(test_obj, params): return response -TEST_USERS_GROUP = 'test_users_group' +TEST_USER_GROUP = 'test_users_group' -def make_users_group(name=TEST_USERS_GROUP): - gr = UsersGroupModel().create(name=name) - UsersGroupModel().add_user_to_group(users_group=gr, +def make_users_group(name=TEST_USER_GROUP): + gr = UserGroupModel().create(name=name) + UserGroupModel().add_user_to_group(users_group=gr, user=TEST_USER_ADMIN_LOGIN) Session().commit() return gr -def destroy_users_group(name=TEST_USERS_GROUP): - UsersGroupModel().delete(users_group=name, force=True) +def destroy_users_group(name=TEST_USER_GROUP): + UserGroupModel().delete(users_group=name, force=True) Session().commit() @@ -999,10 +999,10 @@ class BaseTestApi(object): def test_api_get_users_group(self): id_, params = _build_data(self.apikey, 'get_users_group', - usersgroupid=TEST_USERS_GROUP) + usersgroupid=TEST_USER_GROUP) response = api_call(self, params) - users_group = UsersGroupModel().get_group(TEST_USERS_GROUP) + users_group = UserGroupModel().get_group(TEST_USER_GROUP) members = [] for user in users_group.members: user = user.user @@ -1021,13 +1021,13 @@ class BaseTestApi(object): response = api_call(self, params) expected = [] - for gr_name in [TEST_USERS_GROUP, 'test_users_group2']: - users_group = UsersGroupModel().get_group(gr_name) + for gr_name in [TEST_USER_GROUP, 'test_users_group2']: + users_group = UserGroupModel().get_group(gr_name) ret = users_group.get_api_data() expected.append(ret) self._compare_ok(id_, expected, given=response.body) - UsersGroupModel().delete(users_group='test_users_group2') + UserGroupModel().delete(users_group='test_users_group2') Session().commit() def test_api_create_users_group(self): @@ -1037,8 +1037,8 @@ class BaseTestApi(object): response = api_call(self, params) ret = { - 'msg': 'created new users group `%s`' % group_name, - 'users_group': jsonify(UsersGroupModel()\ + 'msg': 'created new user group `%s`' % group_name, + 'users_group': jsonify(UserGroupModel()\ .get_by_name(group_name)\ .get_api_data()) } @@ -1049,13 +1049,13 @@ class BaseTestApi(object): def test_api_get_users_group_that_exist(self): id_, params = _build_data(self.apikey, 'create_users_group', - group_name=TEST_USERS_GROUP) + group_name=TEST_USER_GROUP) response = api_call(self, params) - expected = "users group `%s` already exist" % TEST_USERS_GROUP + expected = "user group `%s` already exist" % TEST_USER_GROUP self._compare_error(id_, expected, given=response.body) - @mock.patch.object(UsersGroupModel, 'create', crash) + @mock.patch.object(UserGroupModel, 'create', crash) def test_api_get_users_group_exception_occurred(self): group_name = 'exception_happens' id_, params = _build_data(self.apikey, 'create_users_group', @@ -1067,7 +1067,7 @@ class BaseTestApi(object): def test_api_add_user_to_users_group(self): gr_name = 'test_group' - UsersGroupModel().create(gr_name) + UserGroupModel().create(gr_name) Session().commit() id_, params = _build_data(self.apikey, 'add_user_to_users_group', usersgroupid=gr_name, @@ -1075,13 +1075,13 @@ class BaseTestApi(object): response = api_call(self, params) expected = { - 'msg': 'added member `%s` to users group `%s`' % ( + 'msg': 'added member `%s` to user group `%s`' % ( TEST_USER_ADMIN_LOGIN, gr_name ), 'success': True} self._compare_ok(id_, expected, given=response.body) - UsersGroupModel().delete(users_group=gr_name) + UserGroupModel().delete(users_group=gr_name) Session().commit() def test_api_add_user_to_users_group_that_doesnt_exist(self): @@ -1090,29 +1090,29 @@ class BaseTestApi(object): userid=TEST_USER_ADMIN_LOGIN) response = api_call(self, params) - expected = 'users group `%s` does not exist' % 'false-group' + expected = 'user group `%s` does not exist' % 'false-group' self._compare_error(id_, expected, given=response.body) - @mock.patch.object(UsersGroupModel, 'add_user_to_group', crash) + @mock.patch.object(UserGroupModel, 'add_user_to_group', crash) def test_api_add_user_to_users_group_exception_occurred(self): gr_name = 'test_group' - UsersGroupModel().create(gr_name) + UserGroupModel().create(gr_name) Session().commit() id_, params = _build_data(self.apikey, 'add_user_to_users_group', usersgroupid=gr_name, userid=TEST_USER_ADMIN_LOGIN) response = api_call(self, params) - expected = 'failed to add member to users group `%s`' % gr_name + expected = 'failed to add member to user group `%s`' % gr_name self._compare_error(id_, expected, given=response.body) - UsersGroupModel().delete(users_group=gr_name) + UserGroupModel().delete(users_group=gr_name) Session().commit() def test_api_remove_user_from_users_group(self): gr_name = 'test_group_3' - gr = UsersGroupModel().create(gr_name) - UsersGroupModel().add_user_to_group(gr, user=TEST_USER_ADMIN_LOGIN) + gr = UserGroupModel().create(gr_name) + UserGroupModel().add_user_to_group(gr, user=TEST_USER_ADMIN_LOGIN) Session().commit() id_, params = _build_data(self.apikey, 'remove_user_from_users_group', usersgroupid=gr_name, @@ -1120,30 +1120,30 @@ class BaseTestApi(object): response = api_call(self, params) expected = { - 'msg': 'removed member `%s` from users group `%s`' % ( + 'msg': 'removed member `%s` from user group `%s`' % ( TEST_USER_ADMIN_LOGIN, gr_name ), 'success': True} self._compare_ok(id_, expected, given=response.body) - UsersGroupModel().delete(users_group=gr_name) + UserGroupModel().delete(users_group=gr_name) Session().commit() - @mock.patch.object(UsersGroupModel, 'remove_user_from_group', crash) + @mock.patch.object(UserGroupModel, 'remove_user_from_group', crash) def test_api_remove_user_from_users_group_exception_occurred(self): gr_name = 'test_group_3' - gr = UsersGroupModel().create(gr_name) - UsersGroupModel().add_user_to_group(gr, user=TEST_USER_ADMIN_LOGIN) + gr = UserGroupModel().create(gr_name) + UserGroupModel().add_user_to_group(gr, user=TEST_USER_ADMIN_LOGIN) Session().commit() id_, params = _build_data(self.apikey, 'remove_user_from_users_group', usersgroupid=gr_name, userid=TEST_USER_ADMIN_LOGIN) response = api_call(self, params) - expected = 'failed to remove member from users group `%s`' % gr_name + expected = 'failed to remove member from user group `%s`' % gr_name self._compare_error(id_, expected, given=response.body) - UsersGroupModel().delete(users_group=gr_name) + UserGroupModel().delete(users_group=gr_name) Session().commit() @parameterized.expand([('none', 'repository.none'), @@ -1224,13 +1224,13 @@ class BaseTestApi(object): def test_api_grant_users_group_permission(self, name, perm): id_, params = _build_data(self.apikey, 'grant_users_group_permission', repoid=self.REPO, - usersgroupid=TEST_USERS_GROUP, + usersgroupid=TEST_USER_GROUP, perm=perm) response = api_call(self, params) ret = { - 'msg': 'Granted perm: `%s` for users group: `%s` in repo: `%s`' % ( - perm, TEST_USERS_GROUP, self.REPO + 'msg': 'Granted perm: `%s` for user group: `%s` in repo: `%s`' % ( + perm, TEST_USER_GROUP, self.REPO ), 'success': True } @@ -1241,7 +1241,7 @@ class BaseTestApi(object): perm = 'haha.no.permission' id_, params = _build_data(self.apikey, 'grant_users_group_permission', repoid=self.REPO, - usersgroupid=TEST_USERS_GROUP, + usersgroupid=TEST_USER_GROUP, perm=perm) response = api_call(self, params) @@ -1253,28 +1253,28 @@ class BaseTestApi(object): perm = 'repository.read' id_, params = _build_data(self.apikey, 'grant_users_group_permission', repoid=self.REPO, - usersgroupid=TEST_USERS_GROUP, + usersgroupid=TEST_USER_GROUP, perm=perm) response = api_call(self, params) - expected = 'failed to edit permission for users group: `%s` in repo: `%s`' % ( - TEST_USERS_GROUP, self.REPO + expected = 'failed to edit permission for user group: `%s` in repo: `%s`' % ( + TEST_USER_GROUP, self.REPO ) self._compare_error(id_, expected, given=response.body) def test_api_revoke_users_group_permission(self): RepoModel().grant_users_group_permission(repo=self.REPO, - group_name=TEST_USERS_GROUP, + group_name=TEST_USER_GROUP, perm='repository.read') Session().commit() id_, params = _build_data(self.apikey, 'revoke_users_group_permission', repoid=self.REPO, - usersgroupid=TEST_USERS_GROUP,) + usersgroupid=TEST_USER_GROUP,) response = api_call(self, params) expected = { - 'msg': 'Revoked perm for users group: `%s` in repo: `%s`' % ( - TEST_USERS_GROUP, self.REPO + 'msg': 'Revoked perm for user group: `%s` in repo: `%s`' % ( + TEST_USER_GROUP, self.REPO ), 'success': True } @@ -1285,10 +1285,10 @@ class BaseTestApi(object): id_, params = _build_data(self.apikey, 'revoke_users_group_permission', repoid=self.REPO, - usersgroupid=TEST_USERS_GROUP,) + usersgroupid=TEST_USER_GROUP,) response = api_call(self, params) - expected = 'failed to edit permission for users group: `%s` in repo: `%s`' % ( - TEST_USERS_GROUP, self.REPO + expected = 'failed to edit permission for user group: `%s` in repo: `%s`' % ( + TEST_USER_GROUP, self.REPO ) self._compare_error(id_, expected, given=response.body) diff --git a/rhodecode/tests/functional/test_admin_users_groups.py b/rhodecode/tests/functional/test_admin_users_groups.py --- a/rhodecode/tests/functional/test_admin_users_groups.py +++ b/rhodecode/tests/functional/test_admin_users_groups.py @@ -1,7 +1,7 @@ from rhodecode.tests import * -from rhodecode.model.db import UsersGroup, UsersGroupToPerm, Permission +from rhodecode.model.db import UserGroup, UserGroupToPerm, Permission -TEST_USERS_GROUP = 'admins_test' +TEST_USER_GROUP = 'admins_test' class TestAdminUsersGroupsController(TestController): @@ -15,14 +15,14 @@ class TestAdminUsersGroupsController(Tes def test_create(self): self.log_user() - users_group_name = TEST_USERS_GROUP + users_group_name = TEST_USER_GROUP response = self.app.post(url('users_groups'), {'users_group_name': users_group_name, 'active':True}) response.follow() self.checkSessionFlash(response, - 'created users group %s' % TEST_USERS_GROUP) + 'created user group %s' % TEST_USER_GROUP) def test_new(self): response = self.app.get(url('new_users_group')) @@ -39,50 +39,50 @@ class TestAdminUsersGroupsController(Tes def test_delete(self): self.log_user() - users_group_name = TEST_USERS_GROUP + 'another' + users_group_name = TEST_USER_GROUP + 'another' response = self.app.post(url('users_groups'), {'users_group_name':users_group_name, 'active':True}) response.follow() self.checkSessionFlash(response, - 'created users group %s' % users_group_name) + 'created user group %s' % users_group_name) - gr = self.Session.query(UsersGroup)\ - .filter(UsersGroup.users_group_name == + gr = self.Session.query(UserGroup)\ + .filter(UserGroup.users_group_name == users_group_name).one() response = self.app.delete(url('users_group', id=gr.users_group_id)) - gr = self.Session.query(UsersGroup)\ - .filter(UsersGroup.users_group_name == + gr = self.Session.query(UserGroup)\ + .filter(UserGroup.users_group_name == users_group_name).scalar() self.assertEqual(gr, None) def test_enable_repository_read_on_group(self): self.log_user() - users_group_name = TEST_USERS_GROUP + 'another2' + users_group_name = TEST_USER_GROUP + 'another2' response = self.app.post(url('users_groups'), {'users_group_name': users_group_name, 'active': True}) response.follow() - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) self.checkSessionFlash(response, - 'created users group %s' % users_group_name) + 'created user group %s' % users_group_name) ## ENABLE REPO CREATE ON A GROUP response = self.app.put(url('users_group_perm', id=ug.users_group_id), {'create_repo_perm': True}) response.follow() - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) p = Permission.get_by_key('hg.create.repository') p2 = Permission.get_by_key('hg.fork.none') # check if user has this perms, they should be here since # defaults are on - perms = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group == ug).all() + perms = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group == ug).all() self.assertEqual( [[x.users_group_id, x.permission_id, ] for x in perms], @@ -95,13 +95,13 @@ class TestAdminUsersGroupsController(Tes {}) response.follow() - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) p = Permission.get_by_key('hg.create.none') p2 = Permission.get_by_key('hg.fork.none') # check if user has this perms, they should be here since # defaults are on - perms = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group == ug).all() + perms = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group == ug).all() self.assertEqual( sorted([[x.users_group_id, x.permission_id, ] for x in perms]), @@ -110,18 +110,18 @@ class TestAdminUsersGroupsController(Tes ) # DELETE ! - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) ugid = ug.users_group_id response = self.app.delete(url('users_group', id=ug.users_group_id)) response = response.follow() - gr = self.Session.query(UsersGroup)\ - .filter(UsersGroup.users_group_name == + gr = self.Session.query(UserGroup)\ + .filter(UserGroup.users_group_name == users_group_name).scalar() self.assertEqual(gr, None) p = Permission.get_by_key('hg.create.repository') - perms = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group_id == ugid).all() + perms = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group_id == ugid).all() perms = [[x.users_group_id, x.permission_id, ] for x in perms] self.assertEqual( @@ -131,27 +131,27 @@ class TestAdminUsersGroupsController(Tes def test_enable_repository_fork_on_group(self): self.log_user() - users_group_name = TEST_USERS_GROUP + 'another2' + users_group_name = TEST_USER_GROUP + 'another2' response = self.app.post(url('users_groups'), {'users_group_name': users_group_name, 'active': True}) response.follow() - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) self.checkSessionFlash(response, - 'created users group %s' % users_group_name) + 'created user group %s' % users_group_name) ## ENABLE REPO CREATE ON A GROUP response = self.app.put(url('users_group_perm', id=ug.users_group_id), {'fork_repo_perm': True}) response.follow() - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) p = Permission.get_by_key('hg.create.none') p2 = Permission.get_by_key('hg.fork.repository') # check if user has this perms, they should be here since # defaults are on - perms = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group == ug).all() + perms = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group == ug).all() self.assertEqual( [[x.users_group_id, x.permission_id, ] for x in perms], @@ -164,13 +164,13 @@ class TestAdminUsersGroupsController(Tes {}) response.follow() - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) p = Permission.get_by_key('hg.create.none') p2 = Permission.get_by_key('hg.fork.none') # check if user has this perms, they should be here since # defaults are on - perms = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group == ug).all() + perms = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group == ug).all() self.assertEqual( [[x.users_group_id, x.permission_id, ] for x in perms], @@ -179,18 +179,18 @@ class TestAdminUsersGroupsController(Tes ) # DELETE ! - ug = UsersGroup.get_by_group_name(users_group_name) + ug = UserGroup.get_by_group_name(users_group_name) ugid = ug.users_group_id response = self.app.delete(url('users_group', id=ug.users_group_id)) response = response.follow() - gr = self.Session.query(UsersGroup)\ - .filter(UsersGroup.users_group_name == + gr = self.Session.query(UserGroup)\ + .filter(UserGroup.users_group_name == users_group_name).scalar() self.assertEqual(gr, None) p = Permission.get_by_key('hg.fork.repository') - perms = UsersGroupToPerm.query()\ - .filter(UsersGroupToPerm.users_group_id == ugid).all() + perms = UserGroupToPerm.query()\ + .filter(UserGroupToPerm.users_group_id == ugid).all() perms = [[x.users_group_id, x.permission_id, ] for x in perms] self.assertEqual( diff --git a/rhodecode/tests/functional/test_compare.py b/rhodecode/tests/functional/test_compare.py --- a/rhodecode/tests/functional/test_compare.py +++ b/rhodecode/tests/functional/test_compare.py @@ -120,7 +120,7 @@ class TestCompareController(TestControll ## files response.mustcontain("""file1""" % (repo1.repo_name, rev2, rev1, repo2.repo_name)) #swap - response.mustcontain("""[swap]""" % (repo2.repo_name, rev1, rev2, repo1.repo_name)) + response.mustcontain("""[swap]""" % (repo2.repo_name, rev1, rev2, repo1.repo_name)) def test_compare_forks_on_branch_extra_commits_origin_has_incomming_hg(self): self.log_user() @@ -173,7 +173,7 @@ class TestCompareController(TestControll ## files response.mustcontain("""file1""" % (repo1.repo_name, rev2, rev1, repo2.repo_name)) #swap - response.mustcontain("""[swap]""" % (repo2.repo_name, rev1, rev2, repo1.repo_name)) + response.mustcontain("""[swap]""" % (repo2.repo_name, rev1, rev2, repo1.repo_name)) def test_compare_cherry_pick_changesets_from_bottom(self): diff --git a/rhodecode/tests/functional/test_repos_groups.py b/rhodecode/tests/functional/test_repos_groups.py --- a/rhodecode/tests/functional/test_repos_groups.py +++ b/rhodecode/tests/functional/test_repos_groups.py @@ -6,7 +6,7 @@ class TestReposGroupsController(TestCont def test_index(self): self.log_user() response = self.app.get(url('repos_groups')) - response.mustcontain('There are no repositories groups yet') + response.mustcontain('There are no repository groups yet') # def test_index_as_xml(self): # response = self.app.get(url('formatted_repos_groups', format='xml')) diff --git a/rhodecode/tests/models/test_permissions.py b/rhodecode/tests/models/test_permissions.py --- a/rhodecode/tests/models/test_permissions.py +++ b/rhodecode/tests/models/test_permissions.py @@ -4,11 +4,11 @@ from rhodecode.tests import * from rhodecode.tests.models.common import _make_group from rhodecode.model.repos_group import ReposGroupModel from rhodecode.model.repo import RepoModel -from rhodecode.model.db import RepoGroup, User, UsersGroupRepoGroupToPerm +from rhodecode.model.db import RepoGroup, User, UserGroupRepoGroupToPerm from rhodecode.model.user import UserModel from rhodecode.model.meta import Session -from rhodecode.model.users_group import UsersGroupModel +from rhodecode.model.users_group import UserGroupModel from rhodecode.lib.auth import AuthUser from rhodecode.tests.api.api_base import create_repo @@ -51,7 +51,7 @@ class TestPermissions(unittest.TestCase) ReposGroupModel().delete(self.g2.group_id) if hasattr(self, 'ug1'): - UsersGroupModel().delete(self.ug1, force=True) + UserGroupModel().delete(self.ug1, force=True) Session().commit() @@ -124,10 +124,10 @@ class TestPermissions(unittest.TestCase) def test_propagated_permission_from_users_group_by_explicit_perms_exist(self): # make group - self.ug1 = UsersGroupModel().create('G1') + self.ug1 = UserGroupModel().create('G1') # add user to group - UsersGroupModel().add_user_to_group(self.ug1, self.u1) + UserGroupModel().add_user_to_group(self.ug1, self.u1) # set permission to lower new_perm = 'repository.none' @@ -158,10 +158,10 @@ class TestPermissions(unittest.TestCase) def test_propagated_permission_from_users_group(self): # make group - self.ug1 = UsersGroupModel().create('G1') + self.ug1 = UserGroupModel().create('G1') # add user to group - UsersGroupModel().add_user_to_group(self.ug1, self.u3) + UserGroupModel().add_user_to_group(self.ug1, self.u3) # grant perm for group this should override default permission from user new_perm_gr = 'repository.write' @@ -183,9 +183,9 @@ class TestPermissions(unittest.TestCase) def test_propagated_permission_from_users_group_lower_weight(self): # make group - self.ug1 = UsersGroupModel().create('G1') + self.ug1 = UserGroupModel().create('G1') # add user to group - UsersGroupModel().add_user_to_group(self.ug1, self.u1) + UserGroupModel().add_user_to_group(self.ug1, self.u1) # set permission to lower new_perm_h = 'repository.write' @@ -299,13 +299,13 @@ class TestPermissions(unittest.TestCase) user=self.anon, perm='group.none') # make group - self.ug1 = UsersGroupModel().create('G1') + self.ug1 = UserGroupModel().create('G1') # add user to group - UsersGroupModel().add_user_to_group(self.ug1, self.u1) + UserGroupModel().add_user_to_group(self.ug1, self.u1) Session().commit() # check if user is in the group - membrs = [x.user_id for x in UsersGroupModel().get(self.ug1.users_group_id).members] + membrs = [x.user_id for x in UserGroupModel().get(self.ug1.users_group_id).members] self.assertEqual(membrs, [self.u1.user_id]) # add some user to that group @@ -324,9 +324,9 @@ class TestPermissions(unittest.TestCase) perm='group.read') Session().commit() # check if the - obj = Session().query(UsersGroupRepoGroupToPerm)\ - .filter(UsersGroupRepoGroupToPerm.group == self.g1)\ - .filter(UsersGroupRepoGroupToPerm.users_group == self.ug1)\ + obj = Session().query(UserGroupRepoGroupToPerm)\ + .filter(UserGroupRepoGroupToPerm.group == self.g1)\ + .filter(UserGroupRepoGroupToPerm.users_group == self.ug1)\ .scalar() self.assertEqual(obj.permission.permission_name, 'group.read') @@ -439,10 +439,10 @@ class TestPermissions(unittest.TestCase) u1_auth = AuthUser(user_id=self.u1.user_id) self.assertEqual(u1_auth.permissions['repositories']['myownrepo'], 'repository.admin') - #set his permission as users group, he should still be admin - self.ug1 = UsersGroupModel().create('G1') + #set his permission as user group, he should still be admin + self.ug1 = UserGroupModel().create('G1') # add user to group - UsersGroupModel().add_user_to_group(self.ug1, self.u1) + UserGroupModel().add_user_to_group(self.ug1, self.u1) RepoModel().grant_users_group_permission(repo, group_name=self.ug1, perm='repository.none') diff --git a/rhodecode/tests/models/test_users.py b/rhodecode/tests/models/test_users.py --- a/rhodecode/tests/models/test_users.py +++ b/rhodecode/tests/models/test_users.py @@ -1,12 +1,12 @@ import unittest from rhodecode.tests import * -from rhodecode.model.db import User, UsersGroup, UsersGroupMember, UserEmailMap,\ +from rhodecode.model.db import User, UserGroup, UserGroupMember, UserEmailMap,\ Permission from rhodecode.model.user import UserModel from rhodecode.model.meta import Session -from rhodecode.model.users_group import UsersGroupModel +from rhodecode.model.users_group import UserGroupModel class TestUser(unittest.TestCase): @@ -22,19 +22,19 @@ class TestUser(unittest.TestCase): Session().commit() self.assertEqual(User.get_by_username(u'test_user'), usr) - # make users group - users_group = UsersGroupModel().create('some_example_group') + # make user group + users_group = UserGroupModel().create('some_example_group') Session().commit() - UsersGroupModel().add_user_to_group(users_group, usr) + UserGroupModel().add_user_to_group(users_group, usr) Session().commit() - self.assertEqual(UsersGroup.get(users_group.users_group_id), users_group) - self.assertEqual(UsersGroupMember.query().count(), 1) + self.assertEqual(UserGroup.get(users_group.users_group_id), users_group) + self.assertEqual(UserGroupMember.query().count(), 1) UserModel().delete(usr.user_id) Session().commit() - self.assertEqual(UsersGroupMember.query().all(), []) + self.assertEqual(UserGroupMember.query().all(), []) def test_additonal_email_as_main(self): usr = UserModel().create_or_update(username=u'test_user', diff --git a/rhodecode/tests/models/test_users_group_permissions_on_groups.py b/rhodecode/tests/models/test_users_group_permissions_on_groups.py --- a/rhodecode/tests/models/test_users_group_permissions_on_groups.py +++ b/rhodecode/tests/models/test_users_group_permissions_on_groups.py @@ -10,7 +10,7 @@ from rhodecode.model.meta import Session from nose.tools import with_setup from rhodecode.tests.models.common import _create_project_tree, check_tree_perms, \ _get_perms, _check_expected_count, expected_count, _destroy_project_tree -from rhodecode.model.users_group import UsersGroupModel +from rhodecode.model.users_group import UserGroupModel from rhodecode.model.repo import RepoModel @@ -40,10 +40,10 @@ def setup_module(): Session().commit() test_u2_id = test_u2.user_id - gr1 = UsersGroupModel().create(name='perms_group_1') + gr1 = UserGroupModel().create(name='perms_group_1') Session().commit() test_u2_gr_id = gr1.users_group_id - UsersGroupModel().add_user_to_group(gr1, user=test_u2_id) + UserGroupModel().add_user_to_group(gr1, user=test_u2_id) Session().commit() _get_repo_perms = functools.partial(_get_perms, key='repositories', diff --git a/rhodecode/tests/test_libs.py b/rhodecode/tests/test_libs.py --- a/rhodecode/tests/test_libs.py +++ b/rhodecode/tests/test_libs.py @@ -209,6 +209,21 @@ class TestLibs(unittest.TestCase): grav = gravatar_url(email_address=em, size=24) assert grav == 'https://server.com/%s/%s' % (_md5(em), 24) + def _quick_url(self, text, tmpl="""%s""", url_=None): + """ + Changes `some text url[foo]` => `some text foo + + :param text: + """ + import re + #quickly change expected url[] into a link + URL_PAT = re.compile(r'(?:url\[)(.+?)(?:\])') + + def url_func(match_obj): + _url = match_obj.groups()[0] + return tmpl % (url_ or '/some-url', _url) + return URL_PAT.sub(url_func, text) + @parameterized.expand([ ("", ""), @@ -228,27 +243,48 @@ class TestLibs(unittest.TestCase): "url[ffffffffffff] some text traalaa"), ("""Multi line 123123123123 - some text 123123123123""", + some text 123123123123 + sometimes ! + """, """Multi line url[123123123123] - some text url[123123123123]""") + some text url[123123123123] + sometimes ! + """) ]) def test_urlify_changesets(self, sample, expected): - import re - def fake_url(self, *args, **kwargs): return '/some-url' - #quickly change expected url[] into a link - URL_PAT = re.compile(r'(?:url\[)(.+?)(?:\])') - - def url_func(match_obj): - _url = match_obj.groups()[0] - tmpl = """%s""" - return tmpl % _url - - expected = URL_PAT.sub(url_func, expected) + expected = self._quick_url(expected) with mock.patch('pylons.url', fake_url): from rhodecode.lib.helpers import urlify_changesets self.assertEqual(urlify_changesets(sample, 'repo_name'), expected) + + @parameterized.expand([ + ("", + "", + ""), + ("https://svn.apache.org/repos", + "url[https://svn.apache.org/repos]", + "https://svn.apache.org/repos"), + ("http://svn.apache.org/repos", + "url[http://svn.apache.org/repos]", + "http://svn.apache.org/repos"), + ("from rev a also rev http://google.com", + "from rev a also rev url[http://google.com]", + "http://google.com"), + ("""Multi line + https://foo.bar.com + some text lalala""", + """Multi line + url[https://foo.bar.com] + some text lalala""", + "https://foo.bar.com") + ]) + def test_urlify_test(self, sample, expected, url_): + from rhodecode.lib.helpers import urlify_text + expected = self._quick_url(expected, + tmpl="""%s""", url_=url_) + self.assertEqual(urlify_text(sample), expected) diff --git a/rhodecode/tests/test_validators.py b/rhodecode/tests/test_validators.py --- a/rhodecode/tests/test_validators.py +++ b/rhodecode/tests/test_validators.py @@ -5,7 +5,7 @@ import formencode from rhodecode.tests import * from rhodecode.model import validators as v -from rhodecode.model.users_group import UsersGroupModel +from rhodecode.model.users_group import UserGroupModel from rhodecode.model.meta import Session from rhodecode.model.repos_group import ReposGroupModel @@ -51,25 +51,25 @@ class TestReposGroups(unittest.TestCase) self.assertEqual(TEST_USER_ADMIN_LOGIN, validator.to_python(TEST_USER_ADMIN_LOGIN)) - def test_ValidUsersGroup(self): - validator = v.ValidUsersGroup() + def test_ValidUserGroup(self): + validator = v.ValidUserGroup() self.assertRaises(formencode.Invalid, validator.to_python, 'default') self.assertRaises(formencode.Invalid, validator.to_python, '.,') - gr = UsersGroupModel().create('test') - gr2 = UsersGroupModel().create('tes2') + gr = UserGroupModel().create('test') + gr2 = UserGroupModel().create('tes2') Session.commit() self.assertRaises(formencode.Invalid, validator.to_python, 'test') assert gr.users_group_id != None - validator = v.ValidUsersGroup(edit=True, + validator = v.ValidUserGroup(edit=True, old_data={'users_group_id': gr2.users_group_id}) self.assertRaises(formencode.Invalid, validator.to_python, 'test') self.assertRaises(formencode.Invalid, validator.to_python, 'TesT') self.assertRaises(formencode.Invalid, validator.to_python, 'TEST') - UsersGroupModel().delete(gr) - UsersGroupModel().delete(gr2) + UserGroupModel().delete(gr) + UserGroupModel().delete(gr2) Session.commit() def test_ValidReposGroup(self): diff --git a/setup.py b/setup.py --- a/setup.py +++ b/setup.py @@ -35,11 +35,12 @@ is_windows = __platform__ in _get_meta_v requirements = [ "waitress==0.8.2", "webob==1.0.8", + "webtest==1.4.3", "Pylons==1.0.0", "Beaker==1.6.4", "WebHelpers==1.3", "formencode==1.2.4", - "SQLAlchemy==0.7.9", + "SQLAlchemy==0.7.10", "Mako==0.7.3", "pygments>=1.5", "whoosh>=2.4.0,<2.5",