Changeset - e1370dcb9908
[Not reviewed]
beta
0 2 0
Marcin Kuzminski - 13 years ago 2012-07-16 02:28:02
marcin@python-works.com
Created install_git_hook more verbose version of previos code.
- allows autoupdating hooks in later releases
2 files changed with 56 insertions and 19 deletions:
0 comments (0 inline, 0 general)
rhodecode/model/repo.py
Show inline comments
 
@@ -18,26 +18,24 @@
 
# This program is distributed in the hope that it will be useful,
 
# but WITHOUT ANY WARRANTY; without even the implied warranty of
 
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
# GNU General Public License for more details.
 
#
 
# You should have received a copy of the GNU General Public License
 
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
from __future__ import with_statement
 
import os
 
import shutil
 
import logging
 
import traceback
 
import pkg_resources
 
from os.path import dirname as dn, join as jn
 
from datetime import datetime
 

	
 
from rhodecode.lib.vcs.backends import get_backend
 
from rhodecode.lib.compat import json
 
from rhodecode.lib.utils2 import LazyProperty, safe_str, safe_unicode
 
from rhodecode.lib.caching_query import FromCache
 
from rhodecode.lib.hooks import log_create_repository
 

	
 
from rhodecode.model import BaseModel
 
from rhodecode.model.db import Repository, UserRepoToPerm, User, Permission, \
 
    Statistics, UsersGroup, UsersGroupRepoToPerm, RhodeCodeUi, RepoGroup
 
from rhodecode.lib import helpers as h
 
@@ -275,31 +273,33 @@ class RepoModel(BaseModel):
 
                                                    perm.permission)
 
                else:
 
                    _create_default_perms()
 
            else:
 
                _create_default_perms()
 

	
 
            if not just_db:
 
                self.__create_repo(repo_name, repo_type,
 
                                   repos_group,
 
                                   clone_uri)
 
                log_create_repository(new_repo.get_dict(),
 
                                      created_by=owner.username)
 

	
 
            else:
 
                # install the githook if it's a git repo
 
                if repo_type == 'git':
 
                    ScmModel().install_git_hook(repo=new_repo.scm_instance)
 
            # now automatically start following this repository as owner
 
            ScmModel(self.sa).toggle_following_repo(new_repo.repo_id,
 
                                                    owner.user_id)
 
            return new_repo
 
        except:
 
            print traceback.format_exc()
 
            log.error(traceback.format_exc())
 
            raise
 

	
 
    def create(self, form_data, cur_user, just_db=False, fork=None):
 

	
 
        repo_name = form_data['repo_name_full']
 
        repo_type = form_data['repo_type']
 
        description = form_data['description']
 
        owner = cur_user
 
        private = form_data['private']
 
        clone_uri = form_data.get('clone_uri')
 
        repos_group = form_data['repo_group']
 
@@ -439,24 +439,25 @@ class RepoModel(BaseModel):
 
    def __create_repo(self, repo_name, alias, parent, clone_uri=False):
 
        """
 
        makes repository on filesystem. It's group aware means it'll create
 
        a repository within a group, and alter the paths accordingly of
 
        group location
 

	
 
        :param repo_name:
 
        :param alias:
 
        :param parent_id:
 
        :param clone_uri:
 
        """
 
        from rhodecode.lib.utils import is_valid_repo, is_valid_repos_group
 
        from rhodecode.model.scm import ScmModel
 

	
 
        if parent:
 
            new_parent_path = os.sep.join(parent.full_path_splitted)
 
        else:
 
            new_parent_path = ''
 

	
 
        # we need to make it str for mercurial
 
        repo_path = os.path.join(*map(lambda x: safe_str(x),
 
                                [self.repos_path, new_parent_path, repo_name]))
 

	
 
        # check if this path is not a repository
 
        if is_valid_repo(repo_path, self.repos_path):
 
@@ -467,39 +468,25 @@ class RepoModel(BaseModel):
 
            raise Exception('This path %s is a valid group' % repo_path)
 

	
 
        log.info('creating repo %s in %s @ %s' % (
 
                     repo_name, safe_unicode(repo_path), clone_uri
 
                )
 
        )
 
        backend = get_backend(alias)
 
        if alias == 'hg':
 
            backend(repo_path, create=True, src_url=clone_uri)
 
        elif alias == 'git':
 
            r = backend(repo_path, create=True, src_url=clone_uri, bare=True)
 
            # add rhodecode hook into this repo
 

	
 
            loc = jn(r.path, 'hooks')
 
            if not r.bare:
 
                loc = jn(r.path, '.git', 'hooks')
 
            if not os.path.isdir(loc):
 
                os.makedirs(loc)
 

	
 
            tmpl = pkg_resources.resource_string(
 
                'rhodecode', jn('config', 'post_receive_tmpl.py')
 
            )
 
            _hook_file = jn(loc, 'post-receive')
 
            with open(_hook_file, 'wb') as f:
 
                f.write(tmpl)
 
            os.chmod(_hook_file, 0755)
 

	
 
            ScmModel().install_git_hook(repo=r)
 
        else:
 
            raise Exception('Undefined alias %s' % alias)
 

	
 
    def __rename_repo(self, old, new):
 
        """
 
        renames repository on filesystem
 

	
 
        :param old: old name
 
        :param new: new name
 
        """
 
        log.info('renaming repo from %s to %s' % (old, new))
 

	
rhodecode/model/scm.py
Show inline comments
 
@@ -14,32 +14,36 @@
 
# it under the terms of the GNU General Public License as published by
 
# the Free Software Foundation, either version 3 of the License, or
 
# (at your option) any later version.
 
#
 
# This program is distributed in the hope that it will be useful,
 
# but WITHOUT ANY WARRANTY; without even the implied warranty of
 
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
# GNU General Public License for more details.
 
#
 
# You should have received a copy of the GNU General Public License
 
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
import os
 
import re
 
import time
 
import traceback
 
import logging
 
import cStringIO
 
import pkg_resources
 
from os.path import dirname as dn, join as jn
 

	
 
from sqlalchemy import func
 
from pylons.i18n.translation import _
 

	
 
import rhodecode
 
from rhodecode.lib.vcs import get_backend
 
from rhodecode.lib.vcs.exceptions import RepositoryError
 
from rhodecode.lib.vcs.utils.lazy import LazyProperty
 
from rhodecode.lib.vcs.nodes import FileNode
 

	
 
from rhodecode import BACKENDS
 
from rhodecode.lib import helpers as h
 
from rhodecode.lib.utils2 import safe_str, safe_unicode
 
from rhodecode.lib.auth import HasRepoPermissionAny, HasReposGroupPermissionAny
 
from rhodecode.lib.utils import get_repos as get_filesystem_repos, make_ui, \
 
    action_logger, EmptyChangeset, REMOVED_REPO_PAT
 
from rhodecode.model import BaseModel
 
@@ -536,12 +540,58 @@ class ScmModel(BaseModel):
 
        if repo.alias == 'hg':
 
            bookmarks_group = ([(k, k) for k, v in
 
                                repo.bookmarks.iteritems()], _("Bookmarks"))
 
            hist_l.append(bookmarks_group)
 
            choices.extend([x[0] for x in bookmarks_group[0]])
 

	
 
        tags_group = ([(k, k) for k, v in
 
                       repo.tags.iteritems()], _("Tags"))
 
        hist_l.append(tags_group)
 
        choices.extend([x[0] for x in tags_group[0]])
 

	
 
        return choices, hist_l
 

	
 
    def install_git_hook(self, repo, force_create=False):
 
        """
 
        Creates a rhodecode hook inside a git repository
 

	
 
        :param repo: Instance of VCS repo
 
        :param force_create: Create even if same name hook exists
 
        """
 

	
 
        loc = jn(repo.path, 'hooks')
 
        if not repo.bare:
 
            loc = jn(repo.path, '.git', 'hooks')
 
        if not os.path.isdir(loc):
 
            os.makedirs(loc)
 

	
 
        tmpl = pkg_resources.resource_string(
 
            'rhodecode', jn('config', 'post_receive_tmpl.py')
 
        )
 

	
 
        _hook_file = jn(loc, 'post-receive')
 
        _rhodecode_hook = False
 
        log.debug('Installing git hook in repo %s' % repo)
 
        if os.path.exists(_hook_file):
 
            # let's take a look at this hook, maybe it's rhodecode ?
 
            log.debug('hook exists, checking if it is from rhodecode')
 
            _HOOK_VER_PAT = re.compile(r'^RC_HOOK_VER')
 
            with open(_hook_file, 'rb') as f:
 
                data = f.read()
 
                matches = re.compile(r'(?:%s)\s*=\s*(.*)'
 
                                     % 'RC_HOOK_VER').search(data)
 
                if matches:
 
                    try:
 
                        ver = matches.groups()[0]
 
                        log.debug('got %s it is rhodecode' % (ver))
 
                        _rhodecode_hook = True
 
                    except:
 
                        log.error(traceback.format_exc())
 

	
 
        if _rhodecode_hook or force_create:
 
            log.debug('writing hook file !')
 
            with open(_hook_file, 'wb') as f:
 
                tmpl = tmpl.replace('_TMPL_', rhodecode.__version__)
 
                f.write(tmpl)
 
            os.chmod(_hook_file, 0755)
 
        else:
 
            log.debug('skipping writing hook file')
 
\ No newline at end of file
0 comments (0 inline, 0 general)