-
Notifications
You must be signed in to change notification settings - Fork 7.6k
[replace-across-files] Code review fixes #8137
Conversation
…oResults() and parseQuery() cleanup
* Got rid of unnecessary partial in search-summary-paging.html * Refactored change notifications in Document to _notifyDocumentChange() method, and fix up similar logic in SpecRunnerUtils.createMockActiveDocument() * Moved makeDialogFileList from StringUtils to FileUtils * Renamed "file/item/index" to "fileIndex/itemIndex/matchIndex" for clarity in SearchResultsView * Return empty array from _getSearchMatches instead of null * Properly debounce document changes when updating search results view * Fix up file rename handling in search results view to use indexOf() instead of match() * Rename "doReplaceAll" event on FindBar to "replaceAll" * Return a promise from FindInFilesUI.searchAndShowResults() * Replace calls to _.filter() and _.map() with native JS calls * Lots of comment/JSDoc improvements
… every time Also fixes a long-standing bug in updating line numbers for existing result matches.
The last two commits are reasonably semantic, so it might be worth reviewing them separately. |
(Also, I added some comments in the last commit, not in the main PR diff.) |
The new update code looks nice after a fast check. But it doesn't look like it is setting or keeping a good state of the collapsed property. I am thinking that it might be easier to have a second |
Makes sense...in fact, the collapsed state really shouldn't be in the model anyway, since it's a transient view property. I don't think this refactoring introduces any bugs that weren't already there regarding the collapsed state though (since it's still reusing the original info, including the collapsed state, in the same cases it was before, I think), so I'd be inclined to do that fix separately later. |
The only new issue I can see is that the collapsed property is never initialized, since it was initialized when adding the results matches. That should result in a bug when trying to access it. |
It should just evaluate to undefined, which is falsy, so there shouldn't be a problem. I just realized there aren't any tests for the collapse behavior and I didn't manually test it, so I'll double check that, but the panel did come up with no issues when I tested it (and with the collapsed value undefined) |
@njx I'm seeing 9 FileFilters unit tests fail in this branch. |
Ah, I forgot to run those. I'll run all the tests and see if there are other issues. |
Looks like those might have been tests that were added in master that I got in my last merge. Will fix. |
…Clean up duplicate code.
Unit tests fixed in 2b65a5c. There were some unit test helper functions that got cut-and-pasted, and one copy went stale - refactored it to share those functions as much as possible. (Both pieces of that suite still seem to need separate test windows since they make assumptions about the initial state.) |
@peterflynn Should be ready for review. Note that 2b65a5c is easiest to review with |
* collapsed - Optional: whether the results should be collapsed in the UI (default false). | ||
* @return {boolean} true if at least some matches were added, false if we've hit the limit on how many can be added | ||
*/ | ||
SearchModel.prototype.addResults = function (fullpath, resultInfo) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I wonder if we should have this auto-remove the last results for fullpath
instead of expecting the client to remember to do it every time. It's guaranteed that we'll totally overwrite anything that was previously at this.results[fullpath]
, so it seems safe to deduct it from the count automatically. And in fact, maybe the API should be called something like setResultsForFile(), since it's never additive when results for the file were in the model previously.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we don't make that suggested change, we should probably at least clarify the docs, which currently imply calling this is always purely additive.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You're right - that would be clearer (and is harmless in the case where it's already been removed by a previous call to removeResults()
). Fixed, and also removed the return value since no one was using it and it wasn't semantically clear anyway.
@@ -334,7 +334,7 @@ define(function (require, exports, module) { | |||
// TODO: This needs to be kept in sync with Document._handleEditorChange(). In the | |||
// future, we should fix things so that we either don't need mock documents or that this | |||
// is factored so it will just run in both. | |||
$(this).triggerHandler("change", [this, changeList]); | |||
this._notifyDocumentChange(changeList); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this actually breaks the intended functionality of createMockActiveDocument() -- per the comment above in the function body, the Document isn't supposed to get added to the working set. Once we start dispatching the pub-sub version of the event, DocumentManager will try to add it to the working set. I'm actually a little surprised this doesn't break stuff, since there's no working set in the test runner window (jQuery no-opping to the rescue, I guess?). But it seems like we should either change it back or add a flag arg to the pub-sub event to suppress adding to the working set...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah, I missed that - just thought it was out of sync. I'll revert it and fix up the comment.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, looking at it closely, it doesn't look to me like the Document module's change
event is what causes documents to get added to the working set - it's the _dirtyFlagChange
event.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
(So I'm not going to change this back - please confirm that's ok :))
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good point -- agreed. I wonder if we should augment the comment to point out that's the important part to leave out
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed. I also moved the comment up (both here and in Document) to make it clear that it applies to the whole handler, not just the notifyDocumentChange()
part. (There's already another bit that's out of sync - we don't check _refreshInProgress
in the mock version. I don't know if that would break anything.)
@njx Done reviewing -- just a few comments |
p.s. There were a couple other things that came up that I don't think should hold up this PR:
|
* Got rid of "navigator" and "scope" options to FindBar, since they're redundant with "multifile" * Renamed SearchModel.addResults() to setResults() and made it remove the existing results first if any * Comment clarifications
@peterflynn Ready for re-review. I've added #8160 to the card since I think that's the main one we should fix before shipping. Do you want to file a bug for the placeholder text so we can track that issue as well? |
Also, do you think #8159 is a requirement for this story? Seems like an added feature. |
function _addSearchMatches(fullPath, contents, queryExpr, timestamp) { | ||
var matches = _getSearchMatches(contents, queryExpr); | ||
function _updateSearchMatches(fullPath, contents, queryExpr, timestamp) { | ||
searchModel.removeResults(fullPath); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This and the if
wrapper below can be removed in light of the new setResults()
behavior
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is only used once at this point, so I might even inline it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Note that I can't remove the if
wrapper because we return different values in the two cases.
@njx Done re-reviewing. Just a handful of nits. Do you have cycles for that today? If not lmk and I can do those changes & then merge. Re #8159 -- it's in the story criteria, so I don't think it's adding new scope. But if we run low on time and need to punt it, it seems separable. Bug-wise, I think #8162 is worth looking into for this sprint as well. |
@peterflynn Ready for re-review. You're right about #8159 - I missed it in the criteria. We can leave it on the card for now. |
result.resolve(foundMatches); | ||
var matches = _getSearchMatches(text, searchModel.queryExpr); | ||
if (matches.length) { | ||
searchModel.setResults(file.fullPath, {matches: matches, timestamp: timestamp}); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we still need to setResults() even in the !matches.length
case -- it looks like the call to this from _addSearchResultsForEntry()
could be invoked for files where we have a pre-existing record in the SearchModel, which needs to get updated even if the new result is 0 matches.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yup, good point. I'll actually just call removeResults()
directly in that case.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually, it's nicer if I just hoist the setResults()
call out.
@njx Just one more issue! |
@peterflynn OK, should be ready for another round. In addition to fixing the previous issue (and re-fixing it more nicely :)), I also fixed the filesystem issue I mentioned on IRC. |
Reverted the filesystem "fix" since it was inefficient. I'll file a bug. |
Filed as #8168 |
Wohoo! Ready to roll! |
[replace-across-files] Code review fixes
This addresses most of the code review items from #7705 and #7809. Note that this is a pull into nj/replace-across-files - after this is merged, we'll need to put up another PR to actually merge it into master.
All the small cleanups are in c09eaef and 0f3cb18. In addition, I did two bigger cleanups:
searchModel.results
directly, so that it can keep an accurate count of the number of matches without having to re-count every time results are added.As part of the latter work I added a number of unit tests for the updating code (there was only one before), and in the process I found and fixed a bug in the line number update calculation (which has probably always been there).
There are a few code review issues that I didn't address, but I think we can land the feature without them:
showError()
/showNoResults()
(combine them and/or make showNoResults() less confusing)FindReplace.parseQuery()
replaceText
todoSearchInScope()
- have caller store it separatelySearchResultsView.addPanelListeners()
(see Tom's comment in [replace-across-files] Replace in Files #7809)FindUtils.performReplacements()
back intoFindInFiles.doReplace()
I'll file a bug for these - I don't think they should impede shipping the feature this release.