@recaptime-dev's working patches + fork for Phorge, a community fork of Phabricator. (Upstream dev and stable branches are at upstream/main and upstream/stable respectively.) hq.recaptime.dev/wiki/Phorge
phorge phabricator
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

When replying to a threaded inline, put the new inline in the right place in the thread

Summary:
Fixes T10563. If you have a thread like this:

```
> A
> B
> C
```

...and you reply to "B", we should put the new inline below "B".

We currently do when you reload the page, but the initial edit goes at the bottom always (below "C").

Test Plan: {F4963015}

Reviewers: chad

Reviewed By: chad

Maniphest Tasks: T10563

Differential Revision: https://secure.phabricator.com/D17938

+84 -25
+19 -19
resources/celerity/map.php
··· 13 13 'core.pkg.js' => '0f87a6eb', 14 14 'darkconsole.pkg.js' => '1f9a31bc', 15 15 'differential.pkg.css' => 'ea471cb0', 16 - 'differential.pkg.js' => '4a466790', 16 + 'differential.pkg.js' => '31e1b646', 17 17 'diffusion.pkg.css' => 'b93d9b8c', 18 18 'diffusion.pkg.js' => '84c8f8fd', 19 19 'favicon.ico' => '30672e08', ··· 390 390 'rsrc/js/application/dashboard/behavior-dashboard-move-panels.js' => '408bf173', 391 391 'rsrc/js/application/dashboard/behavior-dashboard-query-panel-select.js' => '453c5375', 392 392 'rsrc/js/application/dashboard/behavior-dashboard-tab-panel.js' => 'd4eecc63', 393 - 'rsrc/js/application/diff/DiffChangeset.js' => '68758d99', 393 + 'rsrc/js/application/diff/DiffChangeset.js' => 'ec32b333', 394 394 'rsrc/js/application/diff/DiffChangesetList.js' => '796922e0', 395 - 'rsrc/js/application/diff/DiffInline.js' => '1afe9760', 395 + 'rsrc/js/application/diff/DiffInline.js' => '3337c065', 396 396 'rsrc/js/application/diff/behavior-preview-link.js' => '051c7832', 397 397 'rsrc/js/application/differential/behavior-comment-preview.js' => 'b064af76', 398 398 'rsrc/js/application/differential/behavior-diff-radios.js' => 'e1ff79b1', ··· 777 777 'phabricator-darklog' => 'c8e1ffe3', 778 778 'phabricator-darkmessage' => 'c48cccdd', 779 779 'phabricator-dashboard-css' => 'fe5b1869', 780 - 'phabricator-diff-changeset' => '68758d99', 780 + 'phabricator-diff-changeset' => 'ec32b333', 781 781 'phabricator-diff-changeset-list' => '796922e0', 782 - 'phabricator-diff-inline' => '1afe9760', 782 + 'phabricator-diff-inline' => '3337c065', 783 783 'phabricator-drag-and-drop-file-upload' => '58dea2fa', 784 784 'phabricator-draggable-list' => 'bea6e7f4', 785 785 'phabricator-fatal-config-template-css' => '8f18fa41', ··· 1028 1028 'javelin-util', 1029 1029 'phabricator-keyboard-shortcut-manager', 1030 1030 ), 1031 - '1afe9760' => array( 1032 - 'javelin-dom', 1033 - ), 1034 1031 '1bd28176' => array( 1035 1032 'javelin-install', 1036 1033 'javelin-dom', ··· 1129 1126 'javelin-stratcom', 1130 1127 'javelin-dom', 1131 1128 'javelin-workflow', 1129 + ), 1130 + '3337c065' => array( 1131 + 'javelin-dom', 1132 1132 ), 1133 1133 '3ab51e2c' => array( 1134 1134 'javelin-behavior', ··· 1403 1403 'javelin-dom', 1404 1404 'phabricator-notification', 1405 1405 ), 1406 - '68758d99' => array( 1407 - 'javelin-dom', 1408 - 'javelin-util', 1409 - 'javelin-stratcom', 1410 - 'javelin-install', 1411 - 'javelin-workflow', 1412 - 'javelin-router', 1413 - 'javelin-behavior-device', 1414 - 'javelin-vector', 1415 - 'phabricator-diff-inline', 1416 - ), 1417 1406 '6882e80a' => array( 1418 1407 'javelin-dom', 1419 1408 ), ··· 2141 2130 'javelin-workflow', 2142 2131 'javelin-dom', 2143 2132 'phabricator-draggable-list', 2133 + ), 2134 + 'ec32b333' => array( 2135 + 'javelin-dom', 2136 + 'javelin-util', 2137 + 'javelin-stratcom', 2138 + 'javelin-install', 2139 + 'javelin-workflow', 2140 + 'javelin-router', 2141 + 'javelin-behavior-device', 2142 + 'javelin-vector', 2143 + 'phabricator-diff-inline', 2144 2144 ), 2145 2145 'eded9ee8' => array( 2146 2146 'javelin-behavior',
+23 -4
webroot/rsrc/js/application/diff/DiffChangeset.js
··· 581 581 }, 582 582 583 583 getInlineByID: function(id) { 584 + return this._queryInline('id', id); 585 + }, 586 + 587 + getInlineByPHID: function(phid) { 588 + return this._queryInline('phid', phid); 589 + }, 590 + 591 + _queryInline: function(field, value) { 584 592 // First, look for the inline in the objects we've already built. 585 - var inline = this._findInlineByID(id); 593 + var inline = this._findInline(field, value); 586 594 if (inline) { 587 595 return inline; 588 596 } ··· 590 598 // If we haven't found a matching inline yet, rebuild all the inlines 591 599 // present in the document, then look again. 592 600 this._rebuildAllInlines(); 593 - return this._findInlineByID(id); 601 + return this._findInline(field, value); 594 602 }, 595 603 596 - _findInlineByID: function(id) { 604 + _findInline: function(field, value) { 597 605 for (var ii = 0; ii < this._inlines.length; ii++) { 598 606 var inline = this._inlines[ii]; 599 - if (inline.getID() == id) { 607 + 608 + var target; 609 + switch (field) { 610 + case 'id': 611 + target = inline.getID(); 612 + break; 613 + case 'phid': 614 + target = inline.getPHID(); 615 + break; 616 + } 617 + 618 + if (target == value) { 600 619 return inline; 601 620 } 602 621 }
+42 -2
webroot/rsrc/js/application/diff/DiffInline.js
··· 63 63 (this.getDisplaySide() == 'right') || 64 64 (data.left != data.right); 65 65 66 + this._replyToCommentPHID = data.replyToCommentPHID; 67 + 66 68 this.setInvisible(false); 67 69 68 70 return this; ··· 100 102 101 103 this._replyToCommentPHID = inline._phid; 102 104 103 - // TODO: This should insert correctly into the thread, not just at the 104 - // bottom. 105 + var changeset = this.getChangeset(); 106 + 107 + // We're going to figure out where in the document to position the new 108 + // inline. Normally, it goes after any existing inline rows (so if 109 + // several inlines reply to the same line, they appear in chronological 110 + // order). 111 + 112 + // However: if inlines are threaded, we want to put the new inline in 113 + // the right place in the thread. This might be somewhere in the middle, 114 + // so we need to do a bit more work to figure it out. 115 + 116 + // To find the right place in the thread, we're going to look for any 117 + // inline which is at or above the level of the comment we're replying 118 + // to. This means we've reached a new fork of the thread, and should 119 + // put our new inline before the comment we found. 120 + var ancestor_map = {}; 121 + var ancestor = inline; 122 + var reply_phid; 123 + while (ancestor) { 124 + reply_phid = ancestor.getReplyToCommentPHID(); 125 + if (!reply_phid) { 126 + break; 127 + } 128 + ancestor_map[reply_phid] = true; 129 + ancestor = changeset.getInlineByPHID(reply_phid); 130 + } 131 + 105 132 var parent_row = inline._row; 106 133 var target_row = parent_row.nextSibling; 107 134 while (target_row && JX.Stratcom.hasSigil(target_row, 'inline-row')) { 135 + var target = changeset.getInlineForRow(target_row); 136 + reply_phid = target.getReplyToCommentPHID(); 137 + 138 + // If we found an inline which is replying directly to some ancestor 139 + // of this new comment, this is where the new rows go. 140 + if (ancestor_map.hasOwnProperty(reply_phid)) { 141 + break; 142 + } 143 + 108 144 target_row = target_row.nextSibling; 109 145 } 110 146 ··· 316 352 317 353 getID: function() { 318 354 return this._id; 355 + }, 356 + 357 + getPHID: function() { 358 + return this._phid; 319 359 }, 320 360 321 361 getChangesetID: function() {