##// END OF EJS Templates
Nicer email notifications about pull-request
marcink -
r2799:493646d3 beta
parent child Browse files
Show More
@@ -0,0 +1,20 b''
1 ## -*- coding: utf-8 -*-
2 <%inherit file="main.html"/>
3
4 User <b>${pr_user_created}</b> opened pull request for repository
5 ${pr_repo_url} and wants you to review changes.
6
7 <div>title: ${pr_title}</div>
8 <div>description:</div>
9 <p>
10 ${body}
11 </p>
12
13 <div>revisions for reviewing</div>
14 <ul>
15 %for r in pr_revisions:
16 <li>${r}</li>
17 %endfor
18 </ul>
19
20 View this pull request here: ${pr_url}
@@ -1,737 +1,739 b''
1 1 .. _changelog:
2 2
3 3 =========
4 4 Changelog
5 5 =========
6 6
7 7
8 8 1.4.1 (**2012-09-04**)
9 9 ----------------------
10 10
11 11 :status: in-progress
12 12 :branch: beta
13 13
14 14 news
15 15 ++++
16 16
17 17 - always put a comment about code-review status change even if user send
18 18 empty data
19 19 - modified_on column saves repository update and it's going to be used
20 20 later for light version of main page ref #500
21 - pull request notifications send much nicer emails with details about pull
22 request
21 23
22 24 fixes
23 25 +++++
24 26
25 27 - fixed migrations of permissions that can lead to inconsistency.
26 Some users sent feedback that after upgrading from older versions issues with updating
27 default permissions occured. RhodeCode detects that now and resets default user
28 permission to initial state if there is a need for that. Also forces users to set
29 the default value for new forking permission.
28 Some users sent feedback that after upgrading from older versions issues
29 with updating default permissions occurred. RhodeCode detects that now and
30 resets default user permission to initial state if there is a need for that.
31 Also forces users to set the default value for new forking permission.
30 32
31 33
32 34 1.4.0 (**2012-09-03**)
33 35 ----------------------
34 36
35 37 news
36 38 ++++
37 39
38 40 - new codereview system
39 41 - email map, allowing users to have multiple email addresses mapped into
40 42 their accounts
41 43 - improved git-hook system. Now all actions for git are logged into journal
42 44 including pushed revisions, user and IP address
43 45 - changed setup-app into setup-rhodecode and added default options to it.
44 46 - new git repos are created as bare now by default
45 47 - #464 added links to groups in permission box
46 48 - #465 mentions autocomplete inside comments boxes
47 49 - #469 added --update-only option to whoosh to re-index only given list
48 50 of repos in index
49 51 - rhodecode-api CLI client
50 52 - new git http protocol replaced buggy dulwich implementation.
51 53 Now based on pygrack & gitweb
52 54 - Improved RSS/ATOM feeds. Discoverable by browsers using proper headers, and
53 55 reformated based on user suggestions. Additional rss/atom feeds for user
54 56 journal
55 57 - various i18n improvements
56 58 - #478 permissions overview for admin in user edit view
57 59 - File view now displays small gravatars off all authors of given file
58 60 - Implemented landing revisions. Each repository will get landing_rev attribute
59 61 that defines 'default' revision/branch for generating readme files
60 62 - Implemented #509, RhodeCode enforces SSL for push/pulling if requested at
61 63 earliest possible call.
62 64 - Import remote svn repositories to mercurial using hgsubversion.
63 65 - Fixed #508 RhodeCode now has a option to explicitly set forking permissions
64 66 - RhodeCode can use alternative server for generating avatar icons
65 67 - implemented repositories locking. Pull locks, push unlocks. Also can be done
66 68 via API calls
67 69 - #538 form for permissions can handle multiple users at once
68 70
69 71 fixes
70 72 +++++
71 73
72 74 - improved translations
73 75 - fixes issue #455 Creating an archive generates an exception on Windows
74 76 - fixes #448 Download ZIP archive keeps file in /tmp open and results
75 77 in out of disk space
76 78 - fixes issue #454 Search results under Windows include proceeding
77 79 backslash
78 80 - fixed issue #450. Rhodecode no longer will crash when bad revision is
79 81 present in journal data.
80 82 - fix for issue #417, git execution was broken on windows for certain
81 83 commands.
82 84 - fixed #413. Don't disable .git directory for bare repos on deleting
83 85 - fixed issue #459. Changed the way of obtaining logger in reindex task.
84 86 - fixed #453 added ID field in whoosh SCHEMA that solves the issue of
85 87 reindexing modified files
86 88 - fixed #481 rhodecode emails are sent without Date header
87 89 - fixed #458 wrong count when no repos are present
88 90 - fixed issue #492 missing `\ No newline at end of file` test at the end of
89 91 new chunk in html diff
90 92 - full text search now works also for commit messages
91 93
92 94 1.3.6 (**2012-05-17**)
93 95 ----------------------
94 96
95 97 news
96 98 ++++
97 99
98 100 - chinese traditional translation
99 101 - changed setup-app into setup-rhodecode and added arguments for auto-setup
100 102 mode that doesn't need user interaction
101 103
102 104 fixes
103 105 +++++
104 106
105 107 - fixed no scm found warning
106 108 - fixed __future__ import error on rcextensions
107 109 - made simplejson required lib for speedup on JSON encoding
108 110 - fixes #449 bad regex could get more than revisions from parsing history
109 111 - don't clear DB session when CELERY_EAGER is turned ON
110 112
111 113 1.3.5 (**2012-05-10**)
112 114 ----------------------
113 115
114 116 news
115 117 ++++
116 118
117 119 - use ext_json for json module
118 120 - unified annotation view with file source view
119 121 - notification improvements, better inbox + css
120 122 - #419 don't strip passwords for login forms, make rhodecode
121 123 more compatible with LDAP servers
122 124 - Added HTTP_X_FORWARDED_FOR as another method of extracting
123 125 IP for pull/push logs. - moved all to base controller
124 126 - #415: Adding comment to changeset causes reload.
125 127 Comments are now added via ajax and doesn't reload the page
126 128 - #374 LDAP config is discarded when LDAP can't be activated
127 129 - limited push/pull operations are now logged for git in the journal
128 130 - bumped mercurial to 2.2.X series
129 131 - added support for displaying submodules in file-browser
130 132 - #421 added bookmarks in changelog view
131 133
132 134 fixes
133 135 +++++
134 136
135 137 - fixed dev-version marker for stable when served from source codes
136 138 - fixed missing permission checks on show forks page
137 139 - #418 cast to unicode fixes in notification objects
138 140 - #426 fixed mention extracting regex
139 141 - fixed remote-pulling for git remotes remopositories
140 142 - fixed #434: Error when accessing files or changesets of a git repository
141 143 with submodules
142 144 - fixed issue with empty APIKEYS for users after registration ref. #438
143 145 - fixed issue with getting README files from git repositories
144 146
145 147 1.3.4 (**2012-03-28**)
146 148 ----------------------
147 149
148 150 news
149 151 ++++
150 152
151 153 - Whoosh logging is now controlled by the .ini files logging setup
152 154 - added clone-url into edit form on /settings page
153 155 - added help text into repo add/edit forms
154 156 - created rcextensions module with additional mappings (ref #322) and
155 157 post push/pull/create repo hooks callbacks
156 158 - implemented #377 Users view for his own permissions on account page
157 159 - #399 added inheritance of permissions for users group on repos groups
158 160 - #401 repository group is automatically pre-selected when adding repos
159 161 inside a repository group
160 162 - added alternative HTTP 403 response when client failed to authenticate. Helps
161 163 solving issues with Mercurial and LDAP
162 164 - #402 removed group prefix from repository name when listing repositories
163 165 inside a group
164 166 - added gravatars into permission view and permissions autocomplete
165 167 - #347 when running multiple RhodeCode instances, properly invalidates cache
166 168 for all registered servers
167 169
168 170 fixes
169 171 +++++
170 172
171 173 - fixed #390 cache invalidation problems on repos inside group
172 174 - fixed #385 clone by ID url was loosing proxy prefix in URL
173 175 - fixed some unicode problems with waitress
174 176 - fixed issue with escaping < and > in changeset commits
175 177 - fixed error occurring during recursive group creation in API
176 178 create_repo function
177 179 - fixed #393 py2.5 fixes for routes url generator
178 180 - fixed #397 Private repository groups shows up before login
179 181 - fixed #396 fixed problems with revoking users in nested groups
180 182 - fixed mysql unicode issues + specified InnoDB as default engine with
181 183 utf8 charset
182 184 - #406 trim long branch/tag names in changelog to not break UI
183 185
184 186 1.3.3 (**2012-03-02**)
185 187 ----------------------
186 188
187 189 news
188 190 ++++
189 191
190 192
191 193 fixes
192 194 +++++
193 195
194 196 - fixed some python2.5 compatibility issues
195 197 - fixed issues with removed repos was accidentally added as groups, after
196 198 full rescan of paths
197 199 - fixes #376 Cannot edit user (using container auth)
198 200 - fixes #378 Invalid image urls on changeset screen with proxy-prefix
199 201 configuration
200 202 - fixed initial sorting of repos inside repo group
201 203 - fixes issue when user tried to resubmit same permission into user/user_groups
202 204 - bumped beaker version that fixes #375 leap error bug
203 205 - fixed raw_changeset for git. It was generated with hg patch headers
204 206 - fixed vcs issue with last_changeset for filenodes
205 207 - fixed missing commit after hook delete
206 208 - fixed #372 issues with git operation detection that caused a security issue
207 209 for git repos
208 210
209 211 1.3.2 (**2012-02-28**)
210 212 ----------------------
211 213
212 214 news
213 215 ++++
214 216
215 217
216 218 fixes
217 219 +++++
218 220
219 221 - fixed git protocol issues with repos-groups
220 222 - fixed git remote repos validator that prevented from cloning remote git repos
221 223 - fixes #370 ending slashes fixes for repo and groups
222 224 - fixes #368 improved git-protocol detection to handle other clients
223 225 - fixes #366 When Setting Repository Group To Blank Repo Group Wont Be
224 226 Moved To Root
225 227 - fixes #371 fixed issues with beaker/sqlalchemy and non-ascii cache keys
226 228 - fixed #373 missing cascade drop on user_group_to_perm table
227 229
228 230 1.3.1 (**2012-02-27**)
229 231 ----------------------
230 232
231 233 news
232 234 ++++
233 235
234 236
235 237 fixes
236 238 +++++
237 239
238 240 - redirection loop occurs when remember-me wasn't checked during login
239 241 - fixes issues with git blob history generation
240 242 - don't fetch branch for git in file history dropdown. Causes unneeded slowness
241 243
242 244 1.3.0 (**2012-02-26**)
243 245 ----------------------
244 246
245 247 news
246 248 ++++
247 249
248 250 - code review, inspired by github code-comments
249 251 - #215 rst and markdown README files support
250 252 - #252 Container-based and proxy pass-through authentication support
251 253 - #44 branch browser. Filtering of changelog by branches
252 254 - mercurial bookmarks support
253 255 - new hover top menu, optimized to add maximum size for important views
254 256 - configurable clone url template with possibility to specify protocol like
255 257 ssh:// or http:// and also manually alter other parts of clone_url.
256 258 - enabled largefiles extension by default
257 259 - optimized summary file pages and saved a lot of unused space in them
258 260 - #239 option to manually mark repository as fork
259 261 - #320 mapping of commit authors to RhodeCode users
260 262 - #304 hashes are displayed using monospace font
261 263 - diff configuration, toggle white lines and context lines
262 264 - #307 configurable diffs, whitespace toggle, increasing context lines
263 265 - sorting on branches, tags and bookmarks using YUI datatable
264 266 - improved file filter on files page
265 267 - implements #330 api method for listing nodes ar particular revision
266 268 - #73 added linking issues in commit messages to chosen issue tracker url
267 269 based on user defined regular expression
268 270 - added linking of changesets in commit messages
269 271 - new compact changelog with expandable commit messages
270 272 - firstname and lastname are optional in user creation
271 273 - #348 added post-create repository hook
272 274 - #212 global encoding settings is now configurable from .ini files
273 275 - #227 added repository groups permissions
274 276 - markdown gets codehilite extensions
275 277 - new API methods, delete_repositories, grante/revoke permissions for groups
276 278 and repos
277 279
278 280
279 281 fixes
280 282 +++++
281 283
282 284 - rewrote dbsession management for atomic operations, and better error handling
283 285 - fixed sorting of repo tables
284 286 - #326 escape of special html entities in diffs
285 287 - normalized user_name => username in api attributes
286 288 - fixes #298 ldap created users with mixed case emails created conflicts
287 289 on saving a form
288 290 - fixes issue when owner of a repo couldn't revoke permissions for users
289 291 and groups
290 292 - fixes #271 rare JSON serialization problem with statistics
291 293 - fixes #337 missing validation check for conflicting names of a group with a
292 294 repositories group
293 295 - #340 fixed session problem for mysql and celery tasks
294 296 - fixed #331 RhodeCode mangles repository names if the a repository group
295 297 contains the "full path" to the repositories
296 298 - #355 RhodeCode doesn't store encrypted LDAP passwords
297 299
298 300 1.2.5 (**2012-01-28**)
299 301 ----------------------
300 302
301 303 news
302 304 ++++
303 305
304 306 fixes
305 307 +++++
306 308
307 309 - #340 Celery complains about MySQL server gone away, added session cleanup
308 310 for celery tasks
309 311 - #341 "scanning for repositories in None" log message during Rescan was missing
310 312 a parameter
311 313 - fixed creating archives with subrepos. Some hooks were triggered during that
312 314 operation leading to crash.
313 315 - fixed missing email in account page.
314 316 - Reverted Mercurial to 2.0.1 for windows due to bug in Mercurial that makes
315 317 forking on windows impossible
316 318
317 319 1.2.4 (**2012-01-19**)
318 320 ----------------------
319 321
320 322 news
321 323 ++++
322 324
323 325 - RhodeCode is bundled with mercurial series 2.0.X by default, with
324 326 full support to largefiles extension. Enabled by default in new installations
325 327 - #329 Ability to Add/Remove Groups to/from a Repository via AP
326 328 - added requires.txt file with requirements
327 329
328 330 fixes
329 331 +++++
330 332
331 333 - fixes db session issues with celery when emailing admins
332 334 - #331 RhodeCode mangles repository names if the a repository group
333 335 contains the "full path" to the repositories
334 336 - #298 Conflicting e-mail addresses for LDAP and RhodeCode users
335 337 - DB session cleanup after hg protocol operations, fixes issues with
336 338 `mysql has gone away` errors
337 339 - #333 doc fixes for get_repo api function
338 340 - #271 rare JSON serialization problem with statistics enabled
339 341 - #337 Fixes issues with validation of repository name conflicting with
340 342 a group name. A proper message is now displayed.
341 343 - #292 made ldap_dn in user edit readonly, to get rid of confusion that field
342 344 doesn't work
343 345 - #316 fixes issues with web description in hgrc files
344 346
345 347 1.2.3 (**2011-11-02**)
346 348 ----------------------
347 349
348 350 news
349 351 ++++
350 352
351 353 - added option to manage repos group for non admin users
352 354 - added following API methods for get_users, create_user, get_users_groups,
353 355 get_users_group, create_users_group, add_user_to_users_groups, get_repos,
354 356 get_repo, create_repo, add_user_to_repo
355 357 - implements #237 added password confirmation for my account
356 358 and admin edit user.
357 359 - implements #291 email notification for global events are now sent to all
358 360 administrator users, and global config email.
359 361
360 362 fixes
361 363 +++++
362 364
363 365 - added option for passing auth method for smtp mailer
364 366 - #276 issue with adding a single user with id>10 to usergroups
365 367 - #277 fixes windows LDAP settings in which missing values breaks the ldap auth
366 368 - #288 fixes managing of repos in a group for non admin user
367 369
368 370 1.2.2 (**2011-10-17**)
369 371 ----------------------
370 372
371 373 news
372 374 ++++
373 375
374 376 - #226 repo groups are available by path instead of numerical id
375 377
376 378 fixes
377 379 +++++
378 380
379 381 - #259 Groups with the same name but with different parent group
380 382 - #260 Put repo in group, then move group to another group -> repo becomes unavailable
381 383 - #258 RhodeCode 1.2 assumes egg folder is writable (lockfiles problems)
382 384 - #265 ldap save fails sometimes on converting attributes to booleans,
383 385 added getter and setter into model that will prevent from this on db model level
384 386 - fixed problems with timestamps issues #251 and #213
385 387 - fixes #266 RhodeCode allows to create repo with the same name and in
386 388 the same parent as group
387 389 - fixes #245 Rescan of the repositories on Windows
388 390 - fixes #248 cannot edit repos inside a group on windows
389 391 - fixes #219 forking problems on windows
390 392
391 393 1.2.1 (**2011-10-08**)
392 394 ----------------------
393 395
394 396 news
395 397 ++++
396 398
397 399
398 400 fixes
399 401 +++++
400 402
401 403 - fixed problems with basic auth and push problems
402 404 - gui fixes
403 405 - fixed logger
404 406
405 407 1.2.0 (**2011-10-07**)
406 408 ----------------------
407 409
408 410 news
409 411 ++++
410 412
411 413 - implemented #47 repository groups
412 414 - implemented #89 Can setup google analytics code from settings menu
413 415 - implemented #91 added nicer looking archive urls with more download options
414 416 like tags, branches
415 417 - implemented #44 into file browsing, and added follow branch option
416 418 - implemented #84 downloads can be enabled/disabled for each repository
417 419 - anonymous repository can be cloned without having to pass default:default
418 420 into clone url
419 421 - fixed #90 whoosh indexer can index chooses repositories passed in command
420 422 line
421 423 - extended journal with day aggregates and paging
422 424 - implemented #107 source code lines highlight ranges
423 425 - implemented #93 customizable changelog on combined revision ranges -
424 426 equivalent of githubs compare view
425 427 - implemented #108 extended and more powerful LDAP configuration
426 428 - implemented #56 users groups
427 429 - major code rewrites optimized codes for speed and memory usage
428 430 - raw and diff downloads are now in git format
429 431 - setup command checks for write access to given path
430 432 - fixed many issues with international characters and unicode. It uses utf8
431 433 decode with replace to provide less errors even with non utf8 encoded strings
432 434 - #125 added API KEY access to feeds
433 435 - #109 Repository can be created from external Mercurial link (aka. remote
434 436 repository, and manually updated (via pull) from admin panel
435 437 - beta git support - push/pull server + basic view for git repos
436 438 - added followers page and forks page
437 439 - server side file creation (with binary file upload interface)
438 440 and edition with commits powered by codemirror
439 441 - #111 file browser file finder, quick lookup files on whole file tree
440 442 - added quick login sliding menu into main page
441 443 - changelog uses lazy loading of affected files details, in some scenarios
442 444 this can improve speed of changelog page dramatically especially for
443 445 larger repositories.
444 446 - implements #214 added support for downloading subrepos in download menu.
445 447 - Added basic API for direct operations on rhodecode via JSON
446 448 - Implemented advanced hook management
447 449
448 450 fixes
449 451 +++++
450 452
451 453 - fixed file browser bug, when switching into given form revision the url was
452 454 not changing
453 455 - fixed propagation to error controller on simplehg and simplegit middlewares
454 456 - fixed error when trying to make a download on empty repository
455 457 - fixed problem with '[' chars in commit messages in journal
456 458 - fixed #99 Unicode errors, on file node paths with non utf-8 characters
457 459 - journal fork fixes
458 460 - removed issue with space inside renamed repository after deletion
459 461 - fixed strange issue on formencode imports
460 462 - fixed #126 Deleting repository on Windows, rename used incompatible chars.
461 463 - #150 fixes for errors on repositories mapped in db but corrupted in
462 464 filesystem
463 465 - fixed problem with ascendant characters in realm #181
464 466 - fixed problem with sqlite file based database connection pool
465 467 - whoosh indexer and code stats share the same dynamic extensions map
466 468 - fixes #188 - relationship delete of repo_to_perm entry on user removal
467 469 - fixes issue #189 Trending source files shows "show more" when no more exist
468 470 - fixes issue #197 Relative paths for pidlocks
469 471 - fixes issue #198 password will require only 3 chars now for login form
470 472 - fixes issue #199 wrong redirection for non admin users after creating a repository
471 473 - fixes issues #202, bad db constraint made impossible to attach same group
472 474 more than one time. Affects only mysql/postgres
473 475 - fixes #218 os.kill patch for windows was missing sig param
474 476 - improved rendering of dag (they are not trimmed anymore when number of
475 477 heads exceeds 5)
476 478
477 479 1.1.8 (**2011-04-12**)
478 480 ----------------------
479 481
480 482 news
481 483 ++++
482 484
483 485 - improved windows support
484 486
485 487 fixes
486 488 +++++
487 489
488 490 - fixed #140 freeze of python dateutil library, since new version is python2.x
489 491 incompatible
490 492 - setup-app will check for write permission in given path
491 493 - cleaned up license info issue #149
492 494 - fixes for issues #137,#116 and problems with unicode and accented characters.
493 495 - fixes crashes on gravatar, when passed in email as unicode
494 496 - fixed tooltip flickering problems
495 497 - fixed came_from redirection on windows
496 498 - fixed logging modules, and sql formatters
497 499 - windows fixes for os.kill issue #133
498 500 - fixes path splitting for windows issues #148
499 501 - fixed issue #143 wrong import on migration to 1.1.X
500 502 - fixed problems with displaying binary files, thanks to Thomas Waldmann
501 503 - removed name from archive files since it's breaking ui for long repo names
502 504 - fixed issue with archive headers sent to browser, thanks to Thomas Waldmann
503 505 - fixed compatibility for 1024px displays, and larger dpi settings, thanks to
504 506 Thomas Waldmann
505 507 - fixed issue #166 summary pager was skipping 10 revisions on second page
506 508
507 509
508 510 1.1.7 (**2011-03-23**)
509 511 ----------------------
510 512
511 513 news
512 514 ++++
513 515
514 516 fixes
515 517 +++++
516 518
517 519 - fixed (again) #136 installation support for FreeBSD
518 520
519 521
520 522 1.1.6 (**2011-03-21**)
521 523 ----------------------
522 524
523 525 news
524 526 ++++
525 527
526 528 fixes
527 529 +++++
528 530
529 531 - fixed #136 installation support for FreeBSD
530 532 - RhodeCode will check for python version during installation
531 533
532 534 1.1.5 (**2011-03-17**)
533 535 ----------------------
534 536
535 537 news
536 538 ++++
537 539
538 540 - basic windows support, by exchanging pybcrypt into sha256 for windows only
539 541 highly inspired by idea of mantis406
540 542
541 543 fixes
542 544 +++++
543 545
544 546 - fixed sorting by author in main page
545 547 - fixed crashes with diffs on binary files
546 548 - fixed #131 problem with boolean values for LDAP
547 549 - fixed #122 mysql problems thanks to striker69
548 550 - fixed problem with errors on calling raw/raw_files/annotate functions
549 551 with unknown revisions
550 552 - fixed returned rawfiles attachment names with international character
551 553 - cleaned out docs, big thanks to Jason Harris
552 554
553 555 1.1.4 (**2011-02-19**)
554 556 ----------------------
555 557
556 558 news
557 559 ++++
558 560
559 561 fixes
560 562 +++++
561 563
562 564 - fixed formencode import problem on settings page, that caused server crash
563 565 when that page was accessed as first after server start
564 566 - journal fixes
565 567 - fixed option to access repository just by entering http://server/<repo_name>
566 568
567 569 1.1.3 (**2011-02-16**)
568 570 ----------------------
569 571
570 572 news
571 573 ++++
572 574
573 575 - implemented #102 allowing the '.' character in username
574 576 - added option to access repository just by entering http://server/<repo_name>
575 577 - celery task ignores result for better performance
576 578
577 579 fixes
578 580 +++++
579 581
580 582 - fixed ehlo command and non auth mail servers on smtp_lib. Thanks to
581 583 apollo13 and Johan Walles
582 584 - small fixes in journal
583 585 - fixed problems with getting setting for celery from .ini files
584 586 - registration, password reset and login boxes share the same title as main
585 587 application now
586 588 - fixed #113: to high permissions to fork repository
587 589 - fixed problem with '[' chars in commit messages in journal
588 590 - removed issue with space inside renamed repository after deletion
589 591 - db transaction fixes when filesystem repository creation failed
590 592 - fixed #106 relation issues on databases different than sqlite
591 593 - fixed static files paths links to use of url() method
592 594
593 595 1.1.2 (**2011-01-12**)
594 596 ----------------------
595 597
596 598 news
597 599 ++++
598 600
599 601
600 602 fixes
601 603 +++++
602 604
603 605 - fixes #98 protection against float division of percentage stats
604 606 - fixed graph bug
605 607 - forced webhelpers version since it was making troubles during installation
606 608
607 609 1.1.1 (**2011-01-06**)
608 610 ----------------------
609 611
610 612 news
611 613 ++++
612 614
613 615 - added force https option into ini files for easier https usage (no need to
614 616 set server headers with this options)
615 617 - small css updates
616 618
617 619 fixes
618 620 +++++
619 621
620 622 - fixed #96 redirect loop on files view on repositories without changesets
621 623 - fixed #97 unicode string passed into server header in special cases (mod_wsgi)
622 624 and server crashed with errors
623 625 - fixed large tooltips problems on main page
624 626 - fixed #92 whoosh indexer is more error proof
625 627
626 628 1.1.0 (**2010-12-18**)
627 629 ----------------------
628 630
629 631 news
630 632 ++++
631 633
632 634 - rewrite of internals for vcs >=0.1.10
633 635 - uses mercurial 1.7 with dotencode disabled for maintaining compatibility
634 636 with older clients
635 637 - anonymous access, authentication via ldap
636 638 - performance upgrade for cached repos list - each repository has its own
637 639 cache that's invalidated when needed.
638 640 - performance upgrades on repositories with large amount of commits (20K+)
639 641 - main page quick filter for filtering repositories
640 642 - user dashboards with ability to follow chosen repositories actions
641 643 - sends email to admin on new user registration
642 644 - added cache/statistics reset options into repository settings
643 645 - more detailed action logger (based on hooks) with pushed changesets lists
644 646 and options to disable those hooks from admin panel
645 647 - introduced new enhanced changelog for merges that shows more accurate results
646 648 - new improved and faster code stats (based on pygments lexers mapping tables,
647 649 showing up to 10 trending sources for each repository. Additionally stats
648 650 can be disabled in repository settings.
649 651 - gui optimizations, fixed application width to 1024px
650 652 - added cut off (for large files/changesets) limit into config files
651 653 - whoosh, celeryd, upgrade moved to paster command
652 654 - other than sqlite database backends can be used
653 655
654 656 fixes
655 657 +++++
656 658
657 659 - fixes #61 forked repo was showing only after cache expired
658 660 - fixes #76 no confirmation on user deletes
659 661 - fixes #66 Name field misspelled
660 662 - fixes #72 block user removal when he owns repositories
661 663 - fixes #69 added password confirmation fields
662 664 - fixes #87 RhodeCode crashes occasionally on updating repository owner
663 665 - fixes #82 broken annotations on files with more than 1 blank line at the end
664 666 - a lot of fixes and tweaks for file browser
665 667 - fixed detached session issues
666 668 - fixed when user had no repos he would see all repos listed in my account
667 669 - fixed ui() instance bug when global hgrc settings was loaded for server
668 670 instance and all hgrc options were merged with our db ui() object
669 671 - numerous small bugfixes
670 672
671 673 (special thanks for TkSoh for detailed feedback)
672 674
673 675
674 676 1.0.2 (**2010-11-12**)
675 677 ----------------------
676 678
677 679 news
678 680 ++++
679 681
680 682 - tested under python2.7
681 683 - bumped sqlalchemy and celery versions
682 684
683 685 fixes
684 686 +++++
685 687
686 688 - fixed #59 missing graph.js
687 689 - fixed repo_size crash when repository had broken symlinks
688 690 - fixed python2.5 crashes.
689 691
690 692
691 693 1.0.1 (**2010-11-10**)
692 694 ----------------------
693 695
694 696 news
695 697 ++++
696 698
697 699 - small css updated
698 700
699 701 fixes
700 702 +++++
701 703
702 704 - fixed #53 python2.5 incompatible enumerate calls
703 705 - fixed #52 disable mercurial extension for web
704 706 - fixed #51 deleting repositories don't delete it's dependent objects
705 707
706 708
707 709 1.0.0 (**2010-11-02**)
708 710 ----------------------
709 711
710 712 - security bugfix simplehg wasn't checking for permissions on commands
711 713 other than pull or push.
712 714 - fixed doubled messages after push or pull in admin journal
713 715 - templating and css corrections, fixed repo switcher on chrome, updated titles
714 716 - admin menu accessible from options menu on repository view
715 717 - permissions cached queries
716 718
717 719 1.0.0rc4 (**2010-10-12**)
718 720 --------------------------
719 721
720 722 - fixed python2.5 missing simplejson imports (thanks to Jens BΓ€ckman)
721 723 - removed cache_manager settings from sqlalchemy meta
722 724 - added sqlalchemy cache settings to ini files
723 725 - validated password length and added second try of failure on paster setup-app
724 726 - fixed setup database destroy prompt even when there was no db
725 727
726 728
727 729 1.0.0rc3 (**2010-10-11**)
728 730 -------------------------
729 731
730 732 - fixed i18n during installation.
731 733
732 734 1.0.0rc2 (**2010-10-11**)
733 735 -------------------------
734 736
735 737 - Disabled dirsize in file browser, it's causing nasty bug when dir renames
736 738 occure. After vcs is fixed it'll be put back again.
737 739 - templating/css rewrites, optimized css. No newline at end of file
@@ -1,274 +1,275 b''
1 1 # -*- coding: utf-8 -*-
2 2 """
3 3 rhodecode.model.notification
4 4 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~
5 5
6 6 Model for notifications
7 7
8 8
9 9 :created_on: Nov 20, 2011
10 10 :author: marcink
11 11 :copyright: (C) 2010-2012 Marcin Kuzminski <marcin@python-works.com>
12 12 :license: GPLv3, see COPYING for more details.
13 13 """
14 14 # This program is free software: you can redistribute it and/or modify
15 15 # it under the terms of the GNU General Public License as published by
16 16 # the Free Software Foundation, either version 3 of the License, or
17 17 # (at your option) any later version.
18 18 #
19 19 # This program is distributed in the hope that it will be useful,
20 20 # but WITHOUT ANY WARRANTY; without even the implied warranty of
21 21 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22 22 # GNU General Public License for more details.
23 23 #
24 24 # You should have received a copy of the GNU General Public License
25 25 # along with this program. If not, see <http://www.gnu.org/licenses/>.
26 26
27 27 import os
28 28 import logging
29 29 import traceback
30 30
31 31 from pylons.i18n.translation import _
32 32
33 33 import rhodecode
34 34 from rhodecode.lib import helpers as h
35 35 from rhodecode.model import BaseModel
36 36 from rhodecode.model.db import Notification, User, UserNotification
37 37
38 38 log = logging.getLogger(__name__)
39 39
40 40
41 41 class NotificationModel(BaseModel):
42 42
43 43 cls = Notification
44 44
45 45 def __get_notification(self, notification):
46 46 if isinstance(notification, Notification):
47 47 return notification
48 48 elif isinstance(notification, (int, long)):
49 49 return Notification.get(notification)
50 50 else:
51 51 if notification:
52 52 raise Exception('notification must be int, long or Instance'
53 53 ' of Notification got %s' % type(notification))
54 54
55 55 def create(self, created_by, subject, body, recipients=None,
56 56 type_=Notification.TYPE_MESSAGE, with_email=True,
57 57 email_kwargs={}):
58 58 """
59 59
60 60 Creates notification of given type
61 61
62 62 :param created_by: int, str or User instance. User who created this
63 63 notification
64 64 :param subject:
65 65 :param body:
66 66 :param recipients: list of int, str or User objects, when None
67 67 is given send to all admins
68 68 :param type_: type of notification
69 69 :param with_email: send email with this notification
70 70 :param email_kwargs: additional dict to pass as args to email template
71 71 """
72 72 from rhodecode.lib.celerylib import tasks, run_task
73 73
74 74 if recipients and not getattr(recipients, '__iter__', False):
75 75 raise Exception('recipients must be a list of iterable')
76 76
77 77 created_by_obj = self._get_user(created_by)
78 78
79 79 if recipients:
80 80 recipients_objs = []
81 81 for u in recipients:
82 82 obj = self._get_user(u)
83 83 if obj:
84 84 recipients_objs.append(obj)
85 85 recipients_objs = set(recipients_objs)
86 86 log.debug('sending notifications %s to %s' % (
87 87 type_, recipients_objs)
88 88 )
89 89 else:
90 90 # empty recipients means to all admins
91 91 recipients_objs = User.query().filter(User.admin == True).all()
92 92 log.debug('sending notifications %s to admins: %s' % (
93 93 type_, recipients_objs)
94 94 )
95 95 notif = Notification.create(
96 96 created_by=created_by_obj, subject=subject,
97 97 body=body, recipients=recipients_objs, type_=type_
98 98 )
99 99
100 100 if with_email is False:
101 101 return notif
102 102
103 103 #don't send email to person who created this comment
104 104 rec_objs = set(recipients_objs).difference(set([created_by_obj]))
105 105
106 106 # send email with notification to all other participants
107 107 for rec in rec_objs:
108 108 email_subject = NotificationModel().make_description(notif, False)
109 109 type_ = type_
110 110 email_body = body
111 111 ## this is passed into template
112 112 kwargs = {'subject': subject, 'body': h.rst_w_mentions(body)}
113 113 kwargs.update(email_kwargs)
114 114 email_body_html = EmailNotificationModel()\
115 115 .get_email_tmpl(type_, **kwargs)
116 116
117 117 run_task(tasks.send_email, rec.email, email_subject, email_body,
118 118 email_body_html)
119 119
120 120 return notif
121 121
122 122 def delete(self, user, notification):
123 123 # we don't want to remove actual notification just the assignment
124 124 try:
125 125 notification = self.__get_notification(notification)
126 126 user = self._get_user(user)
127 127 if notification and user:
128 128 obj = UserNotification.query()\
129 129 .filter(UserNotification.user == user)\
130 130 .filter(UserNotification.notification
131 131 == notification)\
132 132 .one()
133 133 self.sa.delete(obj)
134 134 return True
135 135 except Exception:
136 136 log.error(traceback.format_exc())
137 137 raise
138 138
139 139 def get_for_user(self, user, filter_=None):
140 140 """
141 141 Get mentions for given user, filter them if filter dict is given
142 142
143 143 :param user:
144 144 :type user:
145 145 :param filter:
146 146 """
147 147 user = self._get_user(user)
148 148
149 149 q = UserNotification.query()\
150 150 .filter(UserNotification.user == user)\
151 151 .join((Notification, UserNotification.notification_id ==
152 152 Notification.notification_id))
153 153
154 154 if filter_:
155 155 q = q.filter(Notification.type_.in_(filter_))
156 156
157 157 return q.all()
158 158
159 159 def mark_read(self, user, notification):
160 160 try:
161 161 notification = self.__get_notification(notification)
162 162 user = self._get_user(user)
163 163 if notification and user:
164 164 obj = UserNotification.query()\
165 165 .filter(UserNotification.user == user)\
166 166 .filter(UserNotification.notification
167 167 == notification)\
168 168 .one()
169 169 obj.read = True
170 170 self.sa.add(obj)
171 171 return True
172 172 except Exception:
173 173 log.error(traceback.format_exc())
174 174 raise
175 175
176 176 def mark_all_read_for_user(self, user, filter_=None):
177 177 user = self._get_user(user)
178 178 q = UserNotification.query()\
179 179 .filter(UserNotification.user == user)\
180 180 .filter(UserNotification.read == False)\
181 181 .join((Notification, UserNotification.notification_id ==
182 182 Notification.notification_id))
183 183 if filter_:
184 184 q = q.filter(Notification.type_.in_(filter_))
185 185
186 186 # this is a little inefficient but sqlalchemy doesn't support
187 187 # update on joined tables :(
188 188 for obj in q.all():
189 189 obj.read = True
190 190 self.sa.add(obj)
191 191
192 192 def get_unread_cnt_for_user(self, user):
193 193 user = self._get_user(user)
194 194 return UserNotification.query()\
195 195 .filter(UserNotification.read == False)\
196 196 .filter(UserNotification.user == user).count()
197 197
198 198 def get_unread_for_user(self, user):
199 199 user = self._get_user(user)
200 200 return [x.notification for x in UserNotification.query()\
201 201 .filter(UserNotification.read == False)\
202 202 .filter(UserNotification.user == user).all()]
203 203
204 204 def get_user_notification(self, user, notification):
205 205 user = self._get_user(user)
206 206 notification = self.__get_notification(notification)
207 207
208 208 return UserNotification.query()\
209 209 .filter(UserNotification.notification == notification)\
210 210 .filter(UserNotification.user == user).scalar()
211 211
212 212 def make_description(self, notification, show_age=True):
213 213 """
214 214 Creates a human readable description based on properties
215 215 of notification object
216 216 """
217 217 #alias
218 218 _n = notification
219 219 _map = {
220 220 _n.TYPE_CHANGESET_COMMENT: _('commented on commit'),
221 221 _n.TYPE_MESSAGE: _('sent message'),
222 222 _n.TYPE_MENTION: _('mentioned you'),
223 223 _n.TYPE_REGISTRATION: _('registered in RhodeCode'),
224 224 _n.TYPE_PULL_REQUEST: _('opened new pull request'),
225 225 _n.TYPE_PULL_REQUEST_COMMENT: _('commented on pull request')
226 226 }
227 227
228 228 # action == _map string
229 229 tmpl = "%(user)s %(action)s at %(when)s"
230 230 if show_age:
231 231 when = h.age(notification.created_on)
232 232 else:
233 233 when = h.fmt_date(notification.created_on)
234 234
235 235 data = dict(
236 236 user=notification.created_by_user.username,
237 237 action=_map[notification.type_], when=when,
238 238 )
239 239 return tmpl % data
240 240
241 241
242 242 class EmailNotificationModel(BaseModel):
243 243
244 244 TYPE_CHANGESET_COMMENT = Notification.TYPE_CHANGESET_COMMENT
245 245 TYPE_PASSWORD_RESET = 'passoword_link'
246 246 TYPE_REGISTRATION = Notification.TYPE_REGISTRATION
247 247 TYPE_PULL_REQUEST = Notification.TYPE_PULL_REQUEST
248 248 TYPE_DEFAULT = 'default'
249 249
250 250 def __init__(self):
251 251 self._template_root = rhodecode.CONFIG['pylons.paths']['templates'][0]
252 252 self._tmpl_lookup = rhodecode.CONFIG['pylons.app_globals'].mako_lookup
253 253
254 254 self.email_types = {
255 255 self.TYPE_CHANGESET_COMMENT: 'email_templates/changeset_comment.html',
256 256 self.TYPE_PASSWORD_RESET: 'email_templates/password_reset.html',
257 257 self.TYPE_REGISTRATION: 'email_templates/registration.html',
258 self.TYPE_DEFAULT: 'email_templates/default.html'
258 self.TYPE_DEFAULT: 'email_templates/default.html',
259 self.TYPE_PULL_REQUEST: 'email_templates/pull_request.html',
259 260 }
260 261
261 262 def get_email_tmpl(self, type_, **kwargs):
262 263 """
263 264 return generated template for email based on given type
264 265
265 266 :param type_:
266 267 """
267 268
268 269 base = self.email_types.get(type_, self.email_types[self.TYPE_DEFAULT])
269 270 email_template = self._tmpl_lookup.get_template(base)
270 271 # translator inject
271 272 _kwargs = {'_': _}
272 273 _kwargs.update(kwargs)
273 274 log.debug('rendering tmpl %s with kwargs %s' % (base, _kwargs))
274 275 return email_template.render(**_kwargs)
@@ -1,249 +1,257 b''
1 1 # -*- coding: utf-8 -*-
2 2 """
3 3 rhodecode.model.pull_request
4 4 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~
5 5
6 6 pull request model for RhodeCode
7 7
8 8 :created_on: Jun 6, 2012
9 9 :author: marcink
10 10 :copyright: (C) 2012-2012 Marcin Kuzminski <marcin@python-works.com>
11 11 :license: GPLv3, see COPYING for more details.
12 12 """
13 13 # This program is free software: you can redistribute it and/or modify
14 14 # it under the terms of the GNU General Public License as published by
15 15 # the Free Software Foundation, either version 3 of the License, or
16 16 # (at your option) any later version.
17 17 #
18 18 # This program is distributed in the hope that it will be useful,
19 19 # but WITHOUT ANY WARRANTY; without even the implied warranty of
20 20 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 21 # GNU General Public License for more details.
22 22 #
23 23 # You should have received a copy of the GNU General Public License
24 24 # along with this program. If not, see <http://www.gnu.org/licenses/>.
25 25
26 26 import logging
27 27 import binascii
28 28 import datetime
29 29
30 30 from pylons.i18n.translation import _
31 31
32 32 from rhodecode.model.meta import Session
33 33 from rhodecode.lib import helpers as h
34 34 from rhodecode.model import BaseModel
35 35 from rhodecode.model.db import PullRequest, PullRequestReviewers, Notification
36 36 from rhodecode.model.notification import NotificationModel
37 37 from rhodecode.lib.utils2 import safe_unicode
38 38
39 39 from rhodecode.lib.vcs.utils.hgcompat import discovery, localrepo, scmutil
40 40
41 41 log = logging.getLogger(__name__)
42 42
43 43
44 44 class PullRequestModel(BaseModel):
45 45
46 46 cls = PullRequest
47 47
48 48 def __get_pull_request(self, pull_request):
49 49 return self._get_instance(PullRequest, pull_request)
50 50
51 51 def get_all(self, repo):
52 52 repo = self._get_repo(repo)
53 53 return PullRequest.query().filter(PullRequest.other_repo == repo).all()
54 54
55 55 def create(self, created_by, org_repo, org_ref, other_repo,
56 56 other_ref, revisions, reviewers, title, description=None):
57 57
58 58 created_by_user = self._get_user(created_by)
59 59 org_repo = self._get_repo(org_repo)
60 60 other_repo = self._get_repo(other_repo)
61 61
62 62 new = PullRequest()
63 63 new.org_repo = org_repo
64 64 new.org_ref = org_ref
65 65 new.other_repo = other_repo
66 66 new.other_ref = other_ref
67 67 new.revisions = revisions
68 68 new.title = title
69 69 new.description = description
70 70 new.author = created_by_user
71 71 self.sa.add(new)
72 72 Session().flush()
73 73 #members
74 74 for member in reviewers:
75 75 _usr = self._get_user(member)
76 76 reviewer = PullRequestReviewers(_usr, new)
77 77 self.sa.add(reviewer)
78 78
79 79 #notification to reviewers
80 80 notif = NotificationModel()
81 81
82 pr_url = h.url('pullrequest_show', repo_name=other_repo.repo_name,
83 pull_request_id=new.pull_request_id,
84 qualified=True,
85 )
82 86 subject = safe_unicode(
83 87 h.link_to(
84 88 _('%(user)s wants you to review pull request #%(pr_id)s') % \
85 89 {'user': created_by_user.username,
86 90 'pr_id': new.pull_request_id},
87 h.url('pullrequest_show', repo_name=other_repo.repo_name,
88 pull_request_id=new.pull_request_id,
89 qualified=True,
90 )
91 pr_url
91 92 )
92 93 )
93 94 body = description
95 kwargs = {
96 'pr_title': title,
97 'pr_user_created': h.person(created_by_user.email),
98 'pr_repo_url': h.url('summary_home', repo_name=other_repo.repo_name,
99 qualified=True,),
100 'pr_url': pr_url,
101 'pr_revisions': revisions
102 }
94 103 notif.create(created_by=created_by_user, subject=subject, body=body,
95 104 recipients=reviewers,
96 type_=Notification.TYPE_PULL_REQUEST,)
97
105 type_=Notification.TYPE_PULL_REQUEST, email_kwargs=kwargs)
98 106 return new
99 107
100 108 def update_reviewers(self, pull_request, reviewers_ids):
101 109 reviewers_ids = set(reviewers_ids)
102 110 pull_request = self.__get_pull_request(pull_request)
103 111 current_reviewers = PullRequestReviewers.query()\
104 112 .filter(PullRequestReviewers.pull_request==
105 113 pull_request)\
106 114 .all()
107 115 current_reviewers_ids = set([x.user.user_id for x in current_reviewers])
108 116
109 117 to_add = reviewers_ids.difference(current_reviewers_ids)
110 118 to_remove = current_reviewers_ids.difference(reviewers_ids)
111 119
112 120 log.debug("Adding %s reviewers" % to_add)
113 121 log.debug("Removing %s reviewers" % to_remove)
114 122
115 123 for uid in to_add:
116 124 _usr = self._get_user(uid)
117 125 reviewer = PullRequestReviewers(_usr, pull_request)
118 126 self.sa.add(reviewer)
119 127
120 128 for uid in to_remove:
121 129 reviewer = PullRequestReviewers.query()\
122 130 .filter(PullRequestReviewers.user_id==uid,
123 131 PullRequestReviewers.pull_request==pull_request)\
124 132 .scalar()
125 133 if reviewer:
126 134 self.sa.delete(reviewer)
127 135
128 136 def delete(self, pull_request):
129 137 pull_request = self.__get_pull_request(pull_request)
130 138 Session().delete(pull_request)
131 139
132 140 def close_pull_request(self, pull_request):
133 141 pull_request = self.__get_pull_request(pull_request)
134 142 pull_request.status = PullRequest.STATUS_CLOSED
135 143 pull_request.updated_on = datetime.datetime.now()
136 144 self.sa.add(pull_request)
137 145
138 146 def _get_changesets(self, org_repo, org_ref, other_repo, other_ref,
139 147 discovery_data):
140 148 """
141 149 Returns a list of changesets that are incoming from org_repo@org_ref
142 150 to other_repo@other_ref
143 151
144 152 :param org_repo:
145 153 :type org_repo:
146 154 :param org_ref:
147 155 :type org_ref:
148 156 :param other_repo:
149 157 :type other_repo:
150 158 :param other_ref:
151 159 :type other_ref:
152 160 :param tmp:
153 161 :type tmp:
154 162 """
155 163 changesets = []
156 164 #case two independent repos
157 165 common, incoming, rheads = discovery_data
158 166 if org_repo != other_repo and incoming:
159 167 revs = org_repo._repo.changelog.findmissing(common, rheads)
160 168
161 169 for cs in reversed(map(binascii.hexlify, revs)):
162 170 changesets.append(org_repo.get_changeset(cs))
163 171 else:
164 172 _revset_predicates = {
165 173 'branch': 'branch',
166 174 'book': 'bookmark',
167 175 'tag': 'tag',
168 176 'rev': 'id',
169 177 }
170 178
171 179 revs = [
172 180 "ancestors(%s('%s')) and not ancestors(%s('%s'))" % (
173 181 _revset_predicates[org_ref[0]], org_ref[1],
174 182 _revset_predicates[other_ref[0]], other_ref[1]
175 183 )
176 184 ]
177 185
178 186 out = scmutil.revrange(org_repo._repo, revs)
179 187 for cs in reversed(out):
180 188 changesets.append(org_repo.get_changeset(cs))
181 189
182 190 return changesets
183 191
184 192 def _get_discovery(self, org_repo, org_ref, other_repo, other_ref):
185 193 """
186 194 Get's mercurial discovery data used to calculate difference between
187 195 repos and refs
188 196
189 197 :param org_repo:
190 198 :type org_repo:
191 199 :param org_ref:
192 200 :type org_ref:
193 201 :param other_repo:
194 202 :type other_repo:
195 203 :param other_ref:
196 204 :type other_ref:
197 205 """
198 206
199 207 _org_repo = org_repo._repo
200 208 org_rev_type, org_rev = org_ref
201 209
202 210 _other_repo = other_repo._repo
203 211 other_rev_type, other_rev = other_ref
204 212
205 213 log.debug('Doing discovery for %s@%s vs %s@%s' % (
206 214 org_repo, org_ref, other_repo, other_ref)
207 215 )
208 216 #log.debug('Filter heads are %s[%s]' % ('', org_ref[1]))
209 217 org_peer = localrepo.locallegacypeer(_org_repo.local())
210 218 tmp = discovery.findcommonincoming(
211 219 repo=_other_repo, # other_repo we check for incoming
212 220 remote=org_peer, # org_repo source for incoming
213 221 heads=[_other_repo[other_rev].node(),
214 222 _org_repo[org_rev].node()],
215 223 force=False
216 224 )
217 225 return tmp
218 226
219 227 def get_compare_data(self, org_repo, org_ref, other_repo, other_ref):
220 228 """
221 229 Returns a tuple of incomming changesets, and discoverydata cache
222 230
223 231 :param org_repo:
224 232 :type org_repo:
225 233 :param org_ref:
226 234 :type org_ref:
227 235 :param other_repo:
228 236 :type other_repo:
229 237 :param other_ref:
230 238 :type other_ref:
231 239 """
232 240
233 241 if len(org_ref) != 2 or not isinstance(org_ref, (list, tuple)):
234 242 raise Exception('org_ref must be a two element list/tuple')
235 243
236 244 if len(other_ref) != 2 or not isinstance(org_ref, (list, tuple)):
237 245 raise Exception('other_ref must be a two element list/tuple')
238 246
239 247 discovery_data = self._get_discovery(org_repo.scm_instance,
240 248 org_ref,
241 249 other_repo.scm_instance,
242 250 other_ref)
243 251 cs_ranges = self._get_changesets(org_repo.scm_instance,
244 252 org_ref,
245 253 other_repo.scm_instance,
246 254 other_ref,
247 255 discovery_data)
248 256
249 257 return cs_ranges, discovery_data
General Comments 0
You need to be logged in to leave comments. Login now