Show More
@@ -274,7 +274,8 b' def merge_pull_request(' | |||||
274 |
|
274 | |||
275 | pull_request = get_pull_request_or_error(pullrequestid) |
|
275 | pull_request = get_pull_request_or_error(pullrequestid) | |
276 |
|
276 | |||
277 |
check = MergeCheck.validate( |
|
277 | check = MergeCheck.validate( | |
|
278 | pull_request, user=apiuser, translator=request.translate) | |||
278 | merge_possible = not check.failed |
|
279 | merge_possible = not check.failed | |
279 |
|
280 | |||
280 | if not merge_possible: |
|
281 | if not merge_possible: |
@@ -232,8 +232,8 b' class TestPullrequestsView(object):' | |||||
232 | params={'update_commits': 'true', |
|
232 | params={'update_commits': 'true', | |
233 | 'csrf_token': csrf_token}) |
|
233 | 'csrf_token': csrf_token}) | |
234 |
|
234 | |||
235 | expected_msg = PullRequestModel.UPDATE_STATUS_MESSAGES[ |
|
235 | expected_msg = str(PullRequestModel.UPDATE_STATUS_MESSAGES[ | |
236 | UpdateFailureReason.MISSING_SOURCE_REF] |
|
236 | UpdateFailureReason.MISSING_SOURCE_REF]) | |
237 | assert_session_flash(response, expected_msg, category='error') |
|
237 | assert_session_flash(response, expected_msg, category='error') | |
238 |
|
238 | |||
239 | def test_missing_target_reference(self, pr_util, csrf_token): |
|
239 | def test_missing_target_reference(self, pr_util, csrf_token): |
@@ -362,12 +362,14 b' class RepoPullRequestsView(RepoAppView, ' | |||||
362 |
|
362 | |||
363 | # check merge capabilities |
|
363 | # check merge capabilities | |
364 | _merge_check = MergeCheck.validate( |
|
364 | _merge_check = MergeCheck.validate( | |
365 |
pull_request_latest, user=self._rhodecode_user |
|
365 | pull_request_latest, user=self._rhodecode_user, | |
|
366 | translator=self.request.translate) | |||
366 | c.pr_merge_errors = _merge_check.error_details |
|
367 | c.pr_merge_errors = _merge_check.error_details | |
367 | c.pr_merge_possible = not _merge_check.failed |
|
368 | c.pr_merge_possible = not _merge_check.failed | |
368 | c.pr_merge_message = _merge_check.merge_msg |
|
369 | c.pr_merge_message = _merge_check.merge_msg | |
369 |
|
370 | |||
370 |
c.pr_merge_info = MergeCheck.get_merge_conditions( |
|
371 | c.pr_merge_info = MergeCheck.get_merge_conditions( | |
|
372 | pull_request_latest, translator=self.request.translate) | |||
371 |
|
373 | |||
372 | c.pull_request_review_status = _merge_check.review_status |
|
374 | c.pull_request_review_status = _merge_check.review_status | |
373 | if merge_checks: |
|
375 | if merge_checks: | |
@@ -627,7 +629,7 b' class RepoPullRequestsView(RepoAppView, ' | |||||
627 | try: |
|
629 | try: | |
628 | source_repo_data = PullRequestModel().generate_repo_data( |
|
630 | source_repo_data = PullRequestModel().generate_repo_data( | |
629 | source_repo, commit_id=commit_id, |
|
631 | source_repo, commit_id=commit_id, | |
630 | branch=branch_ref, bookmark=bookmark_ref) |
|
632 | branch=branch_ref, bookmark=bookmark_ref, translator=self.request.translate) | |
631 | except CommitDoesNotExistError as e: |
|
633 | except CommitDoesNotExistError as e: | |
632 | log.exception(e) |
|
634 | log.exception(e) | |
633 | h.flash(_('Commit does not exist'), 'error') |
|
635 | h.flash(_('Commit does not exist'), 'error') | |
@@ -643,7 +645,7 b' class RepoPullRequestsView(RepoAppView, ' | |||||
643 | default_target_repo = source_repo.parent |
|
645 | default_target_repo = source_repo.parent | |
644 |
|
646 | |||
645 | target_repo_data = PullRequestModel().generate_repo_data( |
|
647 | target_repo_data = PullRequestModel().generate_repo_data( | |
646 | default_target_repo) |
|
648 | default_target_repo, translator=self.request.translate) | |
647 |
|
649 | |||
648 | selected_source_ref = source_repo_data['refs']['selected_ref'] |
|
650 | selected_source_ref = source_repo_data['refs']['selected_ref'] | |
649 |
|
651 | |||
@@ -676,7 +678,7 b' class RepoPullRequestsView(RepoAppView, ' | |||||
676 | repo = Repository.get_by_repo_name(target_repo_name) |
|
678 | repo = Repository.get_by_repo_name(target_repo_name) | |
677 | if not repo: |
|
679 | if not repo: | |
678 | raise HTTPNotFound() |
|
680 | raise HTTPNotFound() | |
679 | return PullRequestModel().generate_repo_data(repo) |
|
681 | return PullRequestModel().generate_repo_data(repo, translator=self.request.translate) | |
680 |
|
682 | |||
681 | @LoginRequired() |
|
683 | @LoginRequired() | |
682 | @NotAnonymous() |
|
684 | @NotAnonymous() | |
@@ -806,11 +808,12 b' class RepoPullRequestsView(RepoAppView, ' | |||||
806 |
|
808 | |||
807 | try: |
|
809 | try: | |
808 | pull_request = PullRequestModel().create( |
|
810 | pull_request = PullRequestModel().create( | |
809 |
self._rhodecode_user.user_id, source_repo, source_ref, |
|
811 | self._rhodecode_user.user_id, source_repo, source_ref, | |
810 |
target_ref, commit_ids, reviewers, |
|
812 | target_repo, target_ref, commit_ids, reviewers, | |
811 | description, reviewer_rules |
|
813 | pullrequest_title, description, reviewer_rules | |
812 | ) |
|
814 | ) | |
813 | Session().commit() |
|
815 | Session().commit() | |
|
816 | ||||
814 | h.flash(_('Successfully opened new pull request'), |
|
817 | h.flash(_('Successfully opened new pull request'), | |
815 | category='success') |
|
818 | category='success') | |
816 | except Exception: |
|
819 | except Exception: | |
@@ -938,7 +941,8 b' class RepoPullRequestsView(RepoAppView, ' | |||||
938 | pull_request = PullRequest.get_or_404( |
|
941 | pull_request = PullRequest.get_or_404( | |
939 | self.request.matchdict['pull_request_id']) |
|
942 | self.request.matchdict['pull_request_id']) | |
940 |
|
943 | |||
941 |
check = MergeCheck.validate(pull_request, self._rhodecode_db_user |
|
944 | check = MergeCheck.validate(pull_request, self._rhodecode_db_user, | |
|
945 | translator=self.request.translate) | |||
942 | merge_possible = not check.failed |
|
946 | merge_possible = not check.failed | |
943 |
|
947 | |||
944 | for err_type, error_msg in check.errors: |
|
948 | for err_type, error_msg in check.errors: |
@@ -618,6 +618,9 b' def bootstrap_request(**kwargs):' | |||||
618 | host = kwargs.pop('host', 'example.com:80') |
|
618 | host = kwargs.pop('host', 'example.com:80') | |
619 | domain = kwargs.pop('domain', 'example.com') |
|
619 | domain = kwargs.pop('domain', 'example.com') | |
620 |
|
620 | |||
|
621 | def translate(self, msg): | |||
|
622 | return msg | |||
|
623 | ||||
621 | class TestDummySession(pyramid.testing.DummySession): |
|
624 | class TestDummySession(pyramid.testing.DummySession): | |
622 | def save(*arg, **kw): |
|
625 | def save(*arg, **kw): | |
623 | pass |
|
626 | pass | |
@@ -625,6 +628,7 b' def bootstrap_request(**kwargs):' | |||||
625 | request = TestRequest(**kwargs) |
|
628 | request = TestRequest(**kwargs) | |
626 | request.session = TestDummySession() |
|
629 | request.session = TestDummySession() | |
627 |
|
630 | |||
|
631 | ||||
628 | config = pyramid.testing.setUp(request=request) |
|
632 | config = pyramid.testing.setUp(request=request) | |
629 | add_events_routes(config) |
|
633 | add_events_routes(config) | |
630 | return request |
|
634 | return request |
@@ -23,18 +23,17 b'' | |||||
23 | pull request model for RhodeCode |
|
23 | pull request model for RhodeCode | |
24 | """ |
|
24 | """ | |
25 |
|
25 | |||
26 | from collections import namedtuple |
|
26 | ||
27 | import json |
|
27 | import json | |
28 | import logging |
|
28 | import logging | |
29 | import datetime |
|
29 | import datetime | |
30 | import urllib |
|
30 | import urllib | |
|
31 | import collections | |||
31 |
|
32 | |||
32 | from pylons.i18n.translation import _ |
|
|||
33 | from pylons.i18n.translation import lazy_ugettext |
|
|||
34 | from pyramid.threadlocal import get_current_request |
|
33 | from pyramid.threadlocal import get_current_request | |
35 | from sqlalchemy import or_ |
|
|||
36 |
|
34 | |||
37 | from rhodecode import events |
|
35 | from rhodecode import events | |
|
36 | from rhodecode.translation import lazy_ugettext#, _ | |||
38 | from rhodecode.lib import helpers as h, hooks_utils, diffs |
|
37 | from rhodecode.lib import helpers as h, hooks_utils, diffs | |
39 | from rhodecode.lib import audit_logger |
|
38 | from rhodecode.lib import audit_logger | |
40 | from rhodecode.lib.compat import OrderedDict |
|
39 | from rhodecode.lib.compat import OrderedDict | |
@@ -51,7 +50,7 b' from rhodecode.model import BaseModel' | |||||
51 | from rhodecode.model.changeset_status import ChangesetStatusModel |
|
50 | from rhodecode.model.changeset_status import ChangesetStatusModel | |
52 | from rhodecode.model.comment import CommentsModel |
|
51 | from rhodecode.model.comment import CommentsModel | |
53 | from rhodecode.model.db import ( |
|
52 | from rhodecode.model.db import ( | |
54 | PullRequest, PullRequestReviewers, ChangesetStatus, |
|
53 | or_, PullRequest, PullRequestReviewers, ChangesetStatus, | |
55 | PullRequestVersion, ChangesetComment, Repository) |
|
54 | PullRequestVersion, ChangesetComment, Repository) | |
56 | from rhodecode.model.meta import Session |
|
55 | from rhodecode.model.meta import Session | |
57 | from rhodecode.model.notification import NotificationModel, \ |
|
56 | from rhodecode.model.notification import NotificationModel, \ | |
@@ -65,7 +64,7 b' log = logging.getLogger(__name__)' | |||||
65 |
|
64 | |||
66 | # Data structure to hold the response data when updating commits during a pull |
|
65 | # Data structure to hold the response data when updating commits during a pull | |
67 | # request update. |
|
66 | # request update. | |
68 | UpdateResponse = namedtuple('UpdateResponse', [ |
|
67 | UpdateResponse = collections.namedtuple('UpdateResponse', [ | |
69 | 'executed', 'reason', 'new', 'old', 'changes', |
|
68 | 'executed', 'reason', 'new', 'old', 'changes', | |
70 | 'source_changed', 'target_changed']) |
|
69 | 'source_changed', 'target_changed']) | |
71 |
|
70 | |||
@@ -418,7 +417,8 b' class PullRequestModel(BaseModel):' | |||||
418 |
|
417 | |||
419 | def create(self, created_by, source_repo, source_ref, target_repo, |
|
418 | def create(self, created_by, source_repo, source_ref, target_repo, | |
420 | target_ref, revisions, reviewers, title, description=None, |
|
419 | target_ref, revisions, reviewers, title, description=None, | |
421 | reviewer_data=None): |
|
420 | reviewer_data=None, translator=None): | |
|
421 | translator = translator or get_current_request().translate | |||
422 |
|
422 | |||
423 | created_by_user = self._get_user(created_by) |
|
423 | created_by_user = self._get_user(created_by) | |
424 | source_repo = self._get_repo(source_repo) |
|
424 | source_repo = self._get_repo(source_repo) | |
@@ -466,6 +466,9 b' class PullRequestModel(BaseModel):' | |||||
466 | pull_request=pull_request |
|
466 | pull_request=pull_request | |
467 | ) |
|
467 | ) | |
468 |
|
468 | |||
|
469 | MergeCheck.validate( | |||
|
470 | pull_request, user=created_by_user, translator=translator) | |||
|
471 | ||||
469 | self.notify_reviewers(pull_request, reviewer_ids) |
|
472 | self.notify_reviewers(pull_request, reviewer_ids) | |
470 | self._trigger_pull_request_hook( |
|
473 | self._trigger_pull_request_hook( | |
471 | pull_request, created_by_user, 'create') |
|
474 | pull_request, created_by_user, 'create') | |
@@ -535,13 +538,13 b' class PullRequestModel(BaseModel):' | |||||
535 | log.warn("Merge failed, not updating the pull request.") |
|
538 | log.warn("Merge failed, not updating the pull request.") | |
536 | return merge_state |
|
539 | return merge_state | |
537 |
|
540 | |||
538 | def _merge_pull_request(self, pull_request, user, extras): |
|
541 | def _merge_pull_request(self, pull_request, user, extras, merge_msg=None): | |
539 | target_vcs = pull_request.target_repo.scm_instance() |
|
542 | target_vcs = pull_request.target_repo.scm_instance() | |
540 | source_vcs = pull_request.source_repo.scm_instance() |
|
543 | source_vcs = pull_request.source_repo.scm_instance() | |
541 | target_ref = self._refresh_reference( |
|
544 | target_ref = self._refresh_reference( | |
542 | pull_request.target_ref_parts, target_vcs) |
|
545 | pull_request.target_ref_parts, target_vcs) | |
543 |
|
546 | |||
544 | message = _( |
|
547 | message = merge_msg or ( | |
545 | 'Merge pull request #%(pr_id)s from ' |
|
548 | 'Merge pull request #%(pr_id)s from ' | |
546 | '%(source_repo)s %(source_ref_name)s\n\n %(pr_title)s') % { |
|
549 | '%(source_repo)s %(source_ref_name)s\n\n %(pr_title)s') % { | |
547 | 'pr_id': pull_request.pull_request_id, |
|
550 | 'pr_id': pull_request.pull_request_id, | |
@@ -570,12 +573,13 b' class PullRequestModel(BaseModel):' | |||||
570 | close_branch=close_branch) |
|
573 | close_branch=close_branch) | |
571 | return merge_state |
|
574 | return merge_state | |
572 |
|
575 | |||
573 | def _comment_and_close_pr(self, pull_request, user, merge_state): |
|
576 | def _comment_and_close_pr(self, pull_request, user, merge_state, close_msg=None): | |
574 | pull_request.merge_rev = merge_state.merge_ref.commit_id |
|
577 | pull_request.merge_rev = merge_state.merge_ref.commit_id | |
575 | pull_request.updated_on = datetime.datetime.now() |
|
578 | pull_request.updated_on = datetime.datetime.now() | |
|
579 | close_msg = close_msg or 'Pull request merged and closed' | |||
576 |
|
580 | |||
577 | CommentsModel().create( |
|
581 | CommentsModel().create( | |
578 |
text=unicode( |
|
582 | text=safe_unicode(close_msg), | |
579 | repo=pull_request.target_repo.repo_id, |
|
583 | repo=pull_request.target_repo.repo_id, | |
580 | user=user.user_id, |
|
584 | user=user.user_id, | |
581 | pull_request=pull_request.pull_request_id, |
|
585 | pull_request=pull_request.pull_request_id, | |
@@ -1109,7 +1113,7 b' class PullRequestModel(BaseModel):' | |||||
1109 | status_lbl = ChangesetStatus.get_status_lbl(status) |
|
1113 | status_lbl = ChangesetStatus.get_status_lbl(status) | |
1110 |
|
1114 | |||
1111 | default_message = ( |
|
1115 | default_message = ( | |
1112 |
|
|
1116 | 'Closing with status change {transition_icon} {status}.' | |
1113 | ).format(transition_icon='>', status=status_lbl) |
|
1117 | ).format(transition_icon='>', status=status_lbl) | |
1114 | text = message or default_message |
|
1118 | text = message or default_message | |
1115 |
|
1119 | |||
@@ -1151,13 +1155,16 b' class PullRequestModel(BaseModel):' | |||||
1151 |
|
1155 | |||
1152 | return comment, status |
|
1156 | return comment, status | |
1153 |
|
1157 | |||
1154 | def merge_status(self, pull_request): |
|
1158 | def merge_status(self, pull_request, translator=None): | |
|
1159 | _ = translator or get_current_request().translate | |||
|
1160 | ||||
1155 | if not self._is_merge_enabled(pull_request): |
|
1161 | if not self._is_merge_enabled(pull_request): | |
1156 | return False, _('Server-side pull request merging is disabled.') |
|
1162 | return False, _('Server-side pull request merging is disabled.') | |
1157 | if pull_request.is_closed(): |
|
1163 | if pull_request.is_closed(): | |
1158 | return False, _('This pull request is closed.') |
|
1164 | return False, _('This pull request is closed.') | |
1159 | merge_possible, msg = self._check_repo_requirements( |
|
1165 | merge_possible, msg = self._check_repo_requirements( | |
1160 |
target=pull_request.target_repo, source=pull_request.source_repo |
|
1166 | target=pull_request.target_repo, source=pull_request.source_repo, | |
|
1167 | translator=_) | |||
1161 | if not merge_possible: |
|
1168 | if not merge_possible: | |
1162 | return merge_possible, msg |
|
1169 | return merge_possible, msg | |
1163 |
|
1170 | |||
@@ -1171,12 +1178,13 b' class PullRequestModel(BaseModel):' | |||||
1171 |
|
1178 | |||
1172 | return status |
|
1179 | return status | |
1173 |
|
1180 | |||
1174 | def _check_repo_requirements(self, target, source): |
|
1181 | def _check_repo_requirements(self, target, source, translator): | |
1175 | """ |
|
1182 | """ | |
1176 | Check if `target` and `source` have compatible requirements. |
|
1183 | Check if `target` and `source` have compatible requirements. | |
1177 |
|
1184 | |||
1178 | Currently this is just checking for largefiles. |
|
1185 | Currently this is just checking for largefiles. | |
1179 | """ |
|
1186 | """ | |
|
1187 | _ = translator | |||
1180 | target_has_largefiles = self._has_largefiles(target) |
|
1188 | target_has_largefiles = self._has_largefiles(target) | |
1181 | source_has_largefiles = self._has_largefiles(source) |
|
1189 | source_has_largefiles = self._has_largefiles(source) | |
1182 | merge_possible = True |
|
1190 | merge_possible = True | |
@@ -1282,11 +1290,12 b' class PullRequestModel(BaseModel):' | |||||
1282 | return self.MERGE_STATUS_MESSAGES[status_code] |
|
1290 | return self.MERGE_STATUS_MESSAGES[status_code] | |
1283 |
|
1291 | |||
1284 | def generate_repo_data(self, repo, commit_id=None, branch=None, |
|
1292 | def generate_repo_data(self, repo, commit_id=None, branch=None, | |
1285 | bookmark=None): |
|
1293 | bookmark=None, translator=None): | |
|
1294 | ||||
1286 | all_refs, selected_ref = \ |
|
1295 | all_refs, selected_ref = \ | |
1287 | self._get_repo_pullrequest_sources( |
|
1296 | self._get_repo_pullrequest_sources( | |
1288 | repo.scm_instance(), commit_id=commit_id, |
|
1297 | repo.scm_instance(), commit_id=commit_id, | |
1289 | branch=branch, bookmark=bookmark) |
|
1298 | branch=branch, bookmark=bookmark, translator=translator) | |
1290 |
|
1299 | |||
1291 | refs_select2 = [] |
|
1300 | refs_select2 = [] | |
1292 | for element in all_refs: |
|
1301 | for element in all_refs: | |
@@ -1327,7 +1336,8 b' class PullRequestModel(BaseModel):' | |||||
1327 | pass |
|
1336 | pass | |
1328 |
|
1337 | |||
1329 | def _get_repo_pullrequest_sources( |
|
1338 | def _get_repo_pullrequest_sources( | |
1330 |
self, repo, commit_id=None, branch=None, bookmark=None |
|
1339 | self, repo, commit_id=None, branch=None, bookmark=None, | |
|
1340 | translator=None): | |||
1331 | """ |
|
1341 | """ | |
1332 | Return a structure with repo's interesting commits, suitable for |
|
1342 | Return a structure with repo's interesting commits, suitable for | |
1333 | the selectors in pullrequest controller |
|
1343 | the selectors in pullrequest controller | |
@@ -1338,6 +1348,7 b' class PullRequestModel(BaseModel):' | |||||
1338 | by default - even if closed |
|
1348 | by default - even if closed | |
1339 | :param bookmark: a bookmark that must be in the list and selected |
|
1349 | :param bookmark: a bookmark that must be in the list and selected | |
1340 | """ |
|
1350 | """ | |
|
1351 | _ = translator or get_current_request().translate | |||
1341 |
|
1352 | |||
1342 | commit_id = safe_str(commit_id) if commit_id else None |
|
1353 | commit_id = safe_str(commit_id) if commit_id else None | |
1343 | branch = safe_str(branch) if branch else None |
|
1354 | branch = safe_str(branch) if branch else None | |
@@ -1505,10 +1516,8 b' class MergeCheck(object):' | |||||
1505 | ) |
|
1516 | ) | |
1506 |
|
1517 | |||
1507 | @classmethod |
|
1518 | @classmethod | |
1508 |
def validate(cls, pull_request, user, fail_early=False |
|
1519 | def validate(cls, pull_request, user, translator, fail_early=False): | |
1509 | # if migrated to pyramid... |
|
1520 | _ = translator | |
1510 | # _ = lambda: translator or _ # use passed in translator if any |
|
|||
1511 |
|
||||
1512 | merge_check = cls() |
|
1521 | merge_check = cls() | |
1513 |
|
1522 | |||
1514 | # permissions to merge |
|
1523 | # permissions to merge | |
@@ -1557,7 +1566,8 b' class MergeCheck(object):' | |||||
1557 | return merge_check |
|
1566 | return merge_check | |
1558 |
|
1567 | |||
1559 | # merge possible |
|
1568 | # merge possible | |
1560 |
merge_status, msg = PullRequestModel().merge_status( |
|
1569 | merge_status, msg = PullRequestModel().merge_status( | |
|
1570 | pull_request, translator=translator) | |||
1561 | merge_check.merge_possible = merge_status |
|
1571 | merge_check.merge_possible = merge_status | |
1562 | merge_check.merge_msg = msg |
|
1572 | merge_check.merge_msg = msg | |
1563 | if not merge_status: |
|
1573 | if not merge_status: | |
@@ -1572,7 +1582,8 b' class MergeCheck(object):' | |||||
1572 | return merge_check |
|
1582 | return merge_check | |
1573 |
|
1583 | |||
1574 | @classmethod |
|
1584 | @classmethod | |
1575 | def get_merge_conditions(cls, pull_request): |
|
1585 | def get_merge_conditions(cls, pull_request, translator): | |
|
1586 | _ = translator | |||
1576 | merge_details = {} |
|
1587 | merge_details = {} | |
1577 |
|
1588 | |||
1578 | model = PullRequestModel() |
|
1589 | model = PullRequestModel() | |
@@ -1604,8 +1615,8 b' class MergeCheck(object):' | |||||
1604 |
|
1615 | |||
1605 | return merge_details |
|
1616 | return merge_details | |
1606 |
|
1617 | |||
1607 |
ChangeTuple = namedtuple( |
|
1618 | ChangeTuple = collections.namedtuple( | |
1608 |
|
|
1619 | 'ChangeTuple', ['added', 'common', 'removed', 'total']) | |
1609 |
|
1620 | |||
1610 |
FileChangeTuple = namedtuple( |
|
1621 | FileChangeTuple = collections.namedtuple( | |
1611 |
|
|
1622 | 'FileChangeTuple', ['added', 'modified', 'removed']) |
@@ -160,7 +160,7 b' class TestPullRequestModel(object):' | |||||
160 | status, msg = PullRequestModel().merge_status(pull_request) |
|
160 | status, msg = PullRequestModel().merge_status(pull_request) | |
161 | assert status is True |
|
161 | assert status is True | |
162 | assert msg.eval() == 'This pull request can be automatically merged.' |
|
162 | assert msg.eval() == 'This pull request can be automatically merged.' | |
163 |
self.merge_mock.assert_called_ |
|
163 | self.merge_mock.assert_called_with( | |
164 | pull_request.target_ref_parts, |
|
164 | pull_request.target_ref_parts, | |
165 | pull_request.source_repo.scm_instance(), |
|
165 | pull_request.source_repo.scm_instance(), | |
166 | pull_request.source_ref_parts, self.workspace_id, dry_run=True, |
|
166 | pull_request.source_ref_parts, self.workspace_id, dry_run=True, | |
@@ -189,7 +189,7 b' class TestPullRequestModel(object):' | |||||
189 | assert ( |
|
189 | assert ( | |
190 | msg.eval() == |
|
190 | msg.eval() == | |
191 | 'This pull request cannot be merged because of merge conflicts.') |
|
191 | 'This pull request cannot be merged because of merge conflicts.') | |
192 |
self.merge_mock.assert_called_ |
|
192 | self.merge_mock.assert_called_with( | |
193 | pull_request.target_ref_parts, |
|
193 | pull_request.target_ref_parts, | |
194 | pull_request.source_repo.scm_instance(), |
|
194 | pull_request.source_repo.scm_instance(), | |
195 | pull_request.source_ref_parts, self.workspace_id, dry_run=True, |
|
195 | pull_request.source_ref_parts, self.workspace_id, dry_run=True, | |
@@ -221,7 +221,7 b' class TestPullRequestModel(object):' | |||||
221 | assert msg.eval() == ( |
|
221 | assert msg.eval() == ( | |
222 | 'This pull request cannot be merged because of an unhandled' |
|
222 | 'This pull request cannot be merged because of an unhandled' | |
223 | ' exception.') |
|
223 | ' exception.') | |
224 |
self.merge_mock.assert_called_ |
|
224 | self.merge_mock.assert_called_with( | |
225 | pull_request.target_ref_parts, |
|
225 | pull_request.target_ref_parts, | |
226 | pull_request.source_repo.scm_instance(), |
|
226 | pull_request.source_repo.scm_instance(), | |
227 | pull_request.source_ref_parts, self.workspace_id, dry_run=True, |
|
227 | pull_request.source_ref_parts, self.workspace_id, dry_run=True, | |
@@ -294,7 +294,7 b' class TestPullRequestModel(object):' | |||||
294 | pr_title=safe_unicode(pull_request.title) |
|
294 | pr_title=safe_unicode(pull_request.title) | |
295 | ) |
|
295 | ) | |
296 | ) |
|
296 | ) | |
297 |
self.merge_mock.assert_called_ |
|
297 | self.merge_mock.assert_called_with( | |
298 | pull_request.target_ref_parts, |
|
298 | pull_request.target_ref_parts, | |
299 | pull_request.source_repo.scm_instance(), |
|
299 | pull_request.source_repo.scm_instance(), | |
300 | pull_request.source_ref_parts, self.workspace_id, |
|
300 | pull_request.source_ref_parts, self.workspace_id, | |
@@ -333,7 +333,7 b' class TestPullRequestModel(object):' | |||||
333 | pr_title=safe_unicode(pull_request.title) |
|
333 | pr_title=safe_unicode(pull_request.title) | |
334 | ) |
|
334 | ) | |
335 | ) |
|
335 | ) | |
336 |
self.merge_mock.assert_called_ |
|
336 | self.merge_mock.assert_called_with( | |
337 | pull_request.target_ref_parts, |
|
337 | pull_request.target_ref_parts, | |
338 | pull_request.source_repo.scm_instance(), |
|
338 | pull_request.source_repo.scm_instance(), | |
339 | pull_request.source_ref_parts, self.workspace_id, |
|
339 | pull_request.source_ref_parts, self.workspace_id, |
@@ -27,8 +27,20 b' class LazyString(object):' | |||||
27 | self.args = args |
|
27 | self.args = args | |
28 | self.kw = kw |
|
28 | self.kw = kw | |
29 |
|
29 | |||
|
30 | def eval(self): | |||
|
31 | return _(*self.args, **self.kw) | |||
|
32 | ||||
|
33 | def __unicode__(self): | |||
|
34 | return unicode(self.eval()) | |||
|
35 | ||||
30 | def __str__(self): |
|
36 | def __str__(self): | |
31 |
return |
|
37 | return self.eval() | |
|
38 | ||||
|
39 | def __mod__(self, other): | |||
|
40 | return self.eval() % other | |||
|
41 | ||||
|
42 | def format(self, *args): | |||
|
43 | return self.eval().format(*args) | |||
32 |
|
44 | |||
33 |
|
45 | |||
34 | def lazy_ugettext(*args, **kw): |
|
46 | def lazy_ugettext(*args, **kw): |
General Comments 0
You need to be logged in to leave comments.
Login now