##// END OF EJS Templates
old style: fix text areas in fork dialog...
old style: fix text areas in fork dialog There's no textarea-repo style, so the entry box isn't properly aligned.

File last commit:

r4116:ffd45b18 rhodecode-2.2.5-gpl
r4155:cee56368 rhodecode-2.2.5-gpl
Show More
compare.py
309 lines | 12.4 KiB | text/x-python | PythonLexer
Basic compare-view controller with ref parsing
r2241 # -*- coding: utf-8 -*-
# This program is free software: you can redistribute it and/or modify
# 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/>.
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 """
rhodecode.controllers.compare
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
compare controller for pylons showing differences between two
repos, branches, bookmarks or tips
:created_on: May 6, 2012
:author: marcink
:copyright: (c) 2013 RhodeCode GmbH.
:license: GPLv3, see LICENSE for more details.
"""
Mads Kiilerich
compare: move get_changesets to compare controller where it is used...
r3721
Basic compare-view controller with ref parsing
r2241 import logging
import traceback
Mads Kiilerich
compare: move get_changesets to compare controller where it is used...
r3721 import re
Basic compare-view controller with ref parsing
r2241
Use safe_str on flash messages.
r4077 from webob.exc import HTTPNotFound, HTTPBadRequest
Basic compare-view controller with ref parsing
r2241 from pylons import request, response, session, tmpl_context as c, url
from pylons.controllers.util import abort, redirect
Add check for existing revisions in compare view
r2593 from pylons.i18n.translation import _
Basic compare-view controller with ref parsing
r2241
Add check for existing revisions in compare view
r2593 from rhodecode.lib.vcs.exceptions import EmptyRepositoryError, RepositoryError
Mads Kiilerich
compare: move get_changesets to compare controller where it is used...
r3721 from rhodecode.lib.vcs.utils import safe_str
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 from rhodecode.lib.vcs.utils.hgcompat import unionrepo
Implemented basic compare view(for pull requests) for mercurial.
r2348 from rhodecode.lib import helpers as h
Basic compare-view controller with ref parsing
r2241 from rhodecode.lib.base import BaseRepoController, render
from rhodecode.lib.auth import LoginRequired, HasRepoPermissionAnyDecorator
Mads Kiilerich
unionrepo: update for Mercurial 2.6
r3976 from rhodecode.lib import diffs
Created base for diffing two repositories inside rhodecode
r2337 from rhodecode.model.db import Repository
Optimized look of compare view of changesets....
r3011 from rhodecode.lib.diffs import LimitedDiffContainer
Mads Kiilerich
compare: move get_changesets to compare controller where it is used...
r3721
Basic compare-view controller with ref parsing
r2241
log = logging.getLogger(__name__)
class CompareController(BaseRepoController):
def __before__(self):
super(CompareController, self).__before__()
Mads Kiilerich
compare: resolve revisions in the right repository for diffs between repos
r4039 def __get_rev_or_redirect(self, ref, repo, redirect_after=True,
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 partial=False):
Add check for existing revisions in compare view
r2593 """
Safe way to get changeset if error occur it redirects to changeset with
swap the select values with revisions dynamically when switching the repos on pull request view...
r2847 proper message. If partial is set then don't do redirect raise Exception
instead
Add check for existing revisions in compare view
r2593
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 :param ref:
:param repo:
:param redirect_after:
:param partial:
Add check for existing revisions in compare view
r2593 """
Mads Kiilerich
compare: make __get_cs_or_redirect more exact
r4038 rev = ref[1] # default and used for git
if repo.scm_instance.alias == 'hg':
# lookup up the exact node id
_revset_predicates = {
'branch': 'branch',
'book': 'bookmark',
'tag': 'tag',
'rev': 'id',
}
rev_spec = "max(%s(%%s))" % _revset_predicates[ref[0]]
revs = repo.scm_instance._repo.revs(rev_spec, safe_str(ref[1]))
if revs:
rev = revs[-1]
# else: TODO: just report 'not found'
Add check for existing revisions in compare view
r2593 try:
Mads Kiilerich
compare: resolve revisions in the right repository for diffs between repos
r4039 return repo.scm_instance.get_changeset(rev).raw_id
Add check for existing revisions in compare view
r2593 except EmptyRepositoryError, e:
if not redirect_after:
return None
h.flash(h.literal(_('There are no changesets yet')),
category='warning')
redirect(url('summary_home', repo_name=repo.repo_name))
except RepositoryError, e:
Bumped mercurial version to 2.3...
r2684 log.error(traceback.format_exc())
Use safe_str on flash messages.
r4077 h.flash(safe_str(e), category='warning')
swap the select values with revisions dynamically when switching the repos on pull request view...
r2847 if not partial:
redirect(h.url('summary_home', repo_name=repo.repo_name))
raise HTTPBadRequest()
Add check for existing revisions in compare view
r2593
Mads Kiilerich
compare: let _get_changesets work on the already resolved revisions
r4041 def _get_changesets(self, alias, org_repo, org_rev, other_repo, other_rev, merge):
auth decorators are not used anymore on __before__...
r3749 """
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 Returns a list of changesets that can be merged from org_repo at org_rev
to other_repo at other_rev ... and the ancestor that would be used for merge.
:param org_repo: repo object, that is most likely the orginal repo we forked from
:param org_rev: the revision we want our compare to be made
:param other_repo: repo object, mostl likely the fork of org_repo. It hass
all changesets that we need to obtain
:param other_rev: revision we want out compare to be made on other_repo
auth decorators are not used anymore on __before__...
r3749 """
ancestor = None
Mads Kiilerich
compare: handle revisions and ancestor of empty range in _get_changesets
r4040 if org_rev == other_rev:
changesets = []
if merge:
ancestor = org_rev
elif alias == 'hg':
auth decorators are not used anymore on __before__...
r3749 #case two independent repos
if org_repo != other_repo:
hgrepo = unionrepo.unionrepository(other_repo.baseui,
other_repo.path,
org_repo.path)
# all the changesets we are looking for will be in other_repo,
# so rev numbers from hgrepo can be used in other_repo
#no remote compare do it on the same repository
else:
hgrepo = other_repo._repo
if merge:
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 revs = hgrepo.revs(
"ancestors(id(%s)) and not ancestors(id(%s)) and not id(%s)",
other_rev, org_rev, org_rev)
auth decorators are not used anymore on __before__...
r3749
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 ancestors = hgrepo.revs("ancestor(id(%s), id(%s))", org_rev,
other_rev)
auth decorators are not used anymore on __before__...
r3749 if ancestors:
# pick arbitrary ancestor - but there is usually only one
ancestor = hgrepo[ancestors[0]].hex()
else:
# TODO: have both + and - changesets
Mads Kiilerich
hg: use 'revset injection safe' repo.revs for revsets
r3811 revs = hgrepo.revs("id(%s) :: id(%s) - id(%s)",
org_rev, other_rev, org_rev)
auth decorators are not used anymore on __before__...
r3749
Mads Kiilerich
hg: use 'revset injection safe' repo.revs for revsets
r3811 changesets = [other_repo.get_changeset(rev) for rev in revs]
auth decorators are not used anymore on __before__...
r3749
elif alias == 'git':
It's better to use Exception here than assertion. It plays better with the exception handling software like sentry or errormator
r3783 if org_repo != other_repo:
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 from dulwich.repo import Repo
from dulwich.client import SubprocessGitClient
gitrepo = Repo(org_repo.path)
SubprocessGitClient(thin_packs=False).fetch(other_repo.path, gitrepo)
gitrepo_remote = Repo(other_repo.path)
SubprocessGitClient(thin_packs=False).fetch(org_repo.path, gitrepo_remote)
revs = []
for x in gitrepo_remote.get_walker(include=[other_rev],
exclude=[org_rev]):
revs.append(x.commit.id)
It's better to use Exception here than assertion. It plays better with the exception handling software like sentry or errormator
r3783
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 changesets = [other_repo.get_changeset(rev) for rev in reversed(revs)]
if changesets:
ancestor = changesets[0].parents[0].raw_id
else:
# no changesets from other repo, ancestor is the other_rev
ancestor = other_rev
else:
so, se = org_repo.run_git_command(
'log --reverse --pretty="format: %%H" -s %s..%s'
% (org_rev, other_rev)
)
changesets = [org_repo.get_changeset(cs)
for cs in re.findall(r'[0-9a-fA-F]{40}', so)]
else:
raise Exception('Bad alias only git and hg is allowed')
auth decorators are not used anymore on __before__...
r3749
return changesets, ancestor
@LoginRequired()
@HasRepoPermissionAnyDecorator('repository.read', 'repository.write',
'repository.admin')
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 def index(self, repo_name):
c.compare_home = True
org_repo = c.rhodecode_db_repo.repo_name
other_repo = request.GET.get('other_repo', org_repo)
c.org_repo = Repository.get_by_repo_name(org_repo)
c.other_repo = Repository.get_by_repo_name(other_repo)
c.org_ref = c.other_ref = _('Select changeset')
return render('compare/compare_diff.html')
@LoginRequired()
@HasRepoPermissionAnyDecorator('repository.read', 'repository.write',
'repository.admin')
def compare(self, repo_name, org_ref_type, org_ref, other_ref_type, other_ref):
Mads Kiilerich
compare: minor refactoring and comments
r3443 # org_ref will be evaluated in org_repo
Rewrote url routes to make all validations and parsing for compare view + added compare fork button into forked repos
r2363 org_repo = c.rhodecode_db_repo.repo_name
org_ref = (org_ref_type, org_ref)
Mads Kiilerich
compare: minor refactoring and comments
r3443 # other_ref will be evaluated in other_repo
Rewrote url routes to make all validations and parsing for compare view + added compare fork button into forked repos
r2363 other_ref = (other_ref_type, other_ref)
Mads Kiilerich
compare: rename optional compare_url parameter repo to other_repo...
r3317 other_repo = request.GET.get('other_repo', org_repo)
Mads Kiilerich
compare/pullrequest: introduce merge parameter...
r3486 # If merge is True:
# Show what org would get if merged with other:
# List changesets that are ancestors of other but not of org.
# New changesets in org is thus ignored.
# Diff will be from common ancestor, and merges of org to other will thus be ignored.
# If merge is False:
# Make a raw diff from org to other, no matter if related or not.
# Changesets in one and not in the other will be ignored
merge = bool(request.GET.get('merge'))
Mads Kiilerich
compare: minor refactoring and comments
r3443 # fulldiff disables cut_off_limit
c.fulldiff = request.GET.get('fulldiff')
Mads Kiilerich
compare: cleanup of as_form handling...
r3442 # 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',
Mads Kiilerich
compare: rename optional compare_url parameter repo to other_repo...
r3317 repo_name=other_repo,
org_ref_type=other_ref[0], org_ref=other_ref[1],
fixed broken swap url, and added a test to detect it in feature
r3320 other_repo=org_repo,
Mads Kiilerich
compare/pullrequest: introduce merge parameter...
r3486 other_ref_type=org_ref[0], other_ref=org_ref[1],
merge=merge or '')
Rewrote url routes to make all validations and parsing for compare view + added compare fork button into forked repos
r2363
fixed pull-requests with cherry picking changesets...
r3380 org_repo = Repository.get_by_repo_name(org_repo)
other_repo = Repository.get_by_repo_name(other_repo)
Improved cross repos diffs...
r2362
fixed pull-requests with cherry picking changesets...
r3380 if org_repo is None:
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 msg = 'Could not find org repo %s' % org_repo
log.error(msg)
h.flash(msg, category='error')
return redirect(url('compare_home', repo_name=c.repo_name))
fixed pull-requests with cherry picking changesets...
r3380 if other_repo is None:
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 msg = 'Could not find other repo %s' % other_repo
log.error(msg)
h.flash(msg, category='error')
return redirect(url('compare_home', repo_name=c.repo_name))
Enabled compare engine for tags...
r3010
fixed pull-requests with cherry picking changesets...
r3380 if org_repo.scm_instance.alias != other_repo.scm_instance.alias:
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 msg = 'compare of two different kind of remote repos not available'
log.error(msg)
h.flash(msg, category='error')
return redirect(url('compare_home', repo_name=c.repo_name))
Enabled compare engine for tags...
r3010
Mads Kiilerich
compare: resolve revisions in the right repository for diffs between repos
r4039 org_rev = self.__get_rev_or_redirect(ref=org_ref, repo=org_repo, partial=partial)
other_rev = self.__get_rev_or_redirect(ref=other_ref, repo=other_repo, partial=partial)
move the existing changeset checks bellow other checks else it can throw exceptions for non...
r3615
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 c.compare_home = False
fixed pull-requests with cherry picking changesets...
r3380 c.org_repo = org_repo
c.other_repo = other_repo
c.org_ref = org_ref[1]
c.other_ref = other_ref[1]
c.org_ref_type = org_ref[0]
c.other_ref_type = other_ref[0]
Add check for existing revisions in compare view
r2593
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116 c.cs_ranges, c.ancestor = self._get_changesets(
org_repo.scm_instance.alias, org_repo.scm_instance, org_rev,
other_repo.scm_instance, other_rev, merge)
c.statuses = c.rhodecode_db_repo.statuses(
[x.raw_id for x in c.cs_ranges])
Created base for diffing two repositories inside rhodecode
r2337
Mads Kiilerich
compare: only warn about missing ancestor if a 'merge' diff was requested
r4037 if merge and not c.ancestor:
log.error('Unable to find ancestor revision')
removed assertion about ancestor revision....
r3771
swap the select values with revisions dynamically when switching the repos on pull request view...
r2847 if partial:
created pull-request overview
r2395 return render('compare/compare_cs.html')
Mads Kiilerich
compare/pullrequest: introduce merge parameter...
r3486 if c.ancestor:
assert merge
Mads Kiilerich
compare: show aggregated diff of what will be merged to other repo, using merge ancestor...
r3323 # case we want a simple diff without incoming changesets,
# previewing what will be merged.
Mads Kiilerich
compare/pullrequest: introduce merge parameter...
r3486 # Make the diff on the other repo (which is known to have other_ref)
fixed pull-requests with cherry picking changesets...
r3380 log.debug('Using ancestor %s as org_ref instead of %s'
Mads Kiilerich
compare/pullrequest: introduce merge parameter...
r3486 % (c.ancestor, org_ref))
Mads Kiilerich
compare: resolve revisions in the right repository for diffs between repos
r4039 org_rev = c.ancestor
Mads Kiilerich
compare: swap org and other when they refer to different repos, ie are pull request style...
r3322 org_repo = other_repo
#590 Add GET flag that controls the way the diff are generated, for pull requests we want to use non-bundle based diffs,...
r2892
Mads Kiilerich
compare: minor refactoring and comments
r3443 diff_limit = self.cut_off_limit if not c.fulldiff else None
Basic implementation of cherry picking changesets...
r3023
Mads Kiilerich
diff: cleanup of variables and logging in compare and pullrequests
r3812 log.debug('running diff between %s and %s in %s'
Mads Kiilerich
compare: resolve revisions in the right repository for diffs between repos
r4039 % (org_rev, other_rev, org_repo.scm_instance.path))
Bradley M. Kuhn
Imported some of the GPLv3'd changes from RhodeCode v2.2.5....
r4116
Mads Kiilerich
compare: resolve revisions in the right repository for diffs between repos
r4039 txtdiff = org_repo.scm_instance.get_diff(rev1=org_rev, rev2=other_rev)
Mads Kiilerich
diff: cleanup of variables and logging in compare and pullrequests
r3812 diff_processor = diffs.DiffProcessor(txtdiff or '', format='gitdiff',
Optimized look of compare view of changesets....
r3011 diff_limit=diff_limit)
Implemented basic compare view(for pull requests) for mercurial.
r2348 _parsed = diff_processor.prepare()
Created base for diffing two repositories inside rhodecode
r2337
Optimized look of compare view of changesets....
r3011 c.limited_diff = False
if isinstance(_parsed, LimitedDiffContainer):
c.limited_diff = True
Implemented basic compare view(for pull requests) for mercurial.
r2348 c.files = []
c.changes = {}
Multiple changes for compare system...
r3015 c.lines_added = 0
c.lines_deleted = 0
added changeset review status into repo/branch compare view
r2393 for f in _parsed:
Multiple changes for compare system...
r3015 st = f['stats']
diff parser: redefined operations stats for changes...
r3821 if not st['binary']:
c.lines_added += st['added']
c.lines_deleted += st['deleted']
Implemented basic compare view(for pull requests) for mercurial.
r2348 fid = h.FID('', f['filename'])
c.files.append([fid, f['operation'], f['filename'], f['stats']])
Mads Kiilerich
diff: cleanup of variables and logging in compare and pullrequests
r3812 htmldiff = diff_processor.as_html(enable_comments=False, parsed_lines=[f])
c.changes[fid] = [f['operation'], f['filename'], htmldiff]
Created base for diffing two repositories inside rhodecode
r2337
return render('compare/compare_diff.html')