-
Notifications
You must be signed in to change notification settings - Fork 8.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Management] Handle saved search import better #14625
[Management] Handle saved search import better #14625
Conversation
jenkins, test it |
Copied the src/core_plugins/kibana/public/management/sections/objects/_objects.js to my local and tested the blocker #14592. Import works fine now for my export.json in the bug 14592. |
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.
LGTM ( I tested the blocker)
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 haven't tested this in the browser but overall this LGTM! I have some suggestions on ways to make the code more readable, but nothing here is a blocker.
return; | ||
} | ||
if (swallowErrors && err instanceof SavedObjectNotFound) { | ||
if (err.savedObjectType === 'search') { |
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.
Minor nit, but a switch seems to make slightly more sense here:
switch (err.savedObjectType) {
case 'search':
conflictedSearchDocs.push(doc);
return;
case 'index-pattern':
conflictedIndexPatterns.push({ obj, doc });
return;
@@ -205,8 +205,9 @@ uiModules.get('apps/management') | |||
}) | |||
.then((overwriteAll) => { | |||
const conflictedIndexPatterns = []; |
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.
Can we add a comment above these to provide some context?
// We'll collect all index patterns which {don't correspond to a saved object? are missing? I'm not sure},
// so we can ask the user to {resolve them? reassign them?}. We'll also collect all saved searches
// which {don't correspond exist?}, so we can ask the user to {resolve them? recreate them?}.
const conflictedIndexPatterns = [];
const conflictedSearchDocs = [];
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.
// Collect all index patterns and saved searches referenced in other documents, like visualizations,
// but which have not been imported yet.
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 the naming here is a tad confusing. It makes more sense to call a set of index-patterns that could be associated with a savedsearch conflictedIndexPatterns
, but doesn't make sense for savedsearches. The searchDocs are not conflicted. They just don't exist yet, haven't been imported yet, and so visualizations that reference them can't be imported.
Ideas:
referencedSavedSearches
--> the viz references it. that's all we can say for sure.
notYetImportedSavedSearches
--> this assumes that they will be imported. it could be that someone fucked with the id and the savedsearch doesn't actually exist.
referencedAndNotFoundSavedSearches
-- verbose but accurate?
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 added some comments, does that help clarify this?
|
||
function importDocument(doc) { | ||
function importDocument(swallowErrors, doc) { |
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 mentioned this to @chrisronline on Slack. The side effects of pushing docs into conflictedIndexPatterns
and conflictedSearchDocs
into this function make it difficult to follow the flow of the code, especially since we call this function later and pass in conflictedSearchDocs
.
It looks like the logic within the if (swallowErrors ...)
conditional is the only part which changes from call site to call site. Can we extract this logic into its own function and pass that function in when we need it?
const oldIndexId = obj.searchSource.getOwn('index'); | ||
const newIndexId = objs.find(({ oldId }) => oldId === oldIndexId).newId; | ||
if (newIndexId === oldIndexId) { | ||
// Skip |
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.
Can we add a few words here to elaborate? e.g. The index hasn't changed (or whatever conclusion we can draw from this equality check) so we don't need to {do whatever it is we're doing on line 275}.
Please wait.. i'm testing this as well... |
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.
Couple of naming things, but otherwise, looks good enough for solving this blocker. But I really don't like the code style. If I have some more time, I'll post a refactor PR.
@@ -205,8 +205,9 @@ uiModules.get('apps/management') | |||
}) | |||
.then((overwriteAll) => { | |||
const conflictedIndexPatterns = []; |
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.
// Collect all index patterns and saved searches referenced in other documents, like visualizations,
// but which have not been imported yet.
@@ -205,8 +205,9 @@ uiModules.get('apps/management') | |||
}) | |||
.then((overwriteAll) => { | |||
const conflictedIndexPatterns = []; |
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 the naming here is a tad confusing. It makes more sense to call a set of index-patterns that could be associated with a savedsearch conflictedIndexPatterns
, but doesn't make sense for savedsearches. The searchDocs are not conflicted. They just don't exist yet, haven't been imported yet, and so visualizations that reference them can't be imported.
Ideas:
referencedSavedSearches
--> the viz references it. that's all we can say for sure.
notYetImportedSavedSearches
--> this assumes that they will be imported. it could be that someone fucked with the id and the savedsearch doesn't actually exist.
referencedAndNotFoundSavedSearches
-- verbose but accurate?
conflictedIndexPatterns.push({ obj, doc }); | ||
return; | ||
} | ||
} | ||
// swallow errors here so that the remaining promise chain executes |
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 is so confusing now. I get that we want to swallow errors in the original code--so we can continue execution and use notify
. But the fact that we do that makes passing in a new arg called swallowErrors
not make much sense. Its purpose is to avoid hitting the notify
line. Maybe a better name for that arg is handleConflicts
or collectDocsNotFound
.
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.
Couple of naming things, but otherwise, looks good enough for solving this blocker. But I really don't like the code style. If I have some more time, I'll post a refactor PR.
@chrisronline Can you forward port this today? |
@epixa Sure thing. PRs open and will merge on green CI. |
* Port fixes from #14625 to 6.x * Adding missing test file * Fix linting issue
* Port fixes from #14625 to 7.0 * Fix linting issue
Fixes #14592
This PR changes how we handle the new import conflict handling so we process saved searches separately from other objects (like dashboards and visualizations) to ensure that objects imported that reference saved searches resolve properly.
Specifically, this PR separates saved object import conflicts for saved searches from other saved objects (dashboards, visualizations). This separation then allows us to process the saved searches first to ensure those are written before we attempt to process other saved objects, which could rely on those saved searches to exist.