-
Notifications
You must be signed in to change notification settings - Fork 8.3k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[Ingest Manager ] prepend kibana asset ids with package name (#70502)
* prepend asset ids with package name * fix type * cleanup Co-authored-by: Elastic Machine <[email protected]>
- Loading branch information
1 parent
b8591bc
commit 984ea07
Showing
7 changed files
with
419 additions
and
89 deletions.
There are no files selected for viewing
119 changes: 119 additions & 0 deletions
119
x-pack/plugins/ingest_manager/server/services/epm/kibana/assets/install.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,119 @@ | ||
/* | ||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one | ||
* or more contributor license agreements. Licensed under the Elastic License; | ||
* you may not use this file except in compliance with the Elastic License. | ||
*/ | ||
|
||
import { | ||
SavedObject, | ||
SavedObjectsBulkCreateObject, | ||
SavedObjectsClientContract, | ||
} from 'src/core/server'; | ||
import * as Registry from '../../registry'; | ||
import { AssetType, KibanaAssetType, AssetReference } from '../../../../types'; | ||
|
||
type SavedObjectToBe = Required<SavedObjectsBulkCreateObject> & { type: AssetType }; | ||
export type ArchiveAsset = Pick< | ||
SavedObject, | ||
'id' | 'attributes' | 'migrationVersion' | 'references' | ||
> & { | ||
type: AssetType; | ||
}; | ||
|
||
export async function getKibanaAsset(key: string) { | ||
const buffer = Registry.getAsset(key); | ||
|
||
// cache values are buffers. convert to string / JSON | ||
return JSON.parse(buffer.toString('utf8')); | ||
} | ||
|
||
export function createSavedObjectKibanaAsset( | ||
jsonAsset: ArchiveAsset, | ||
pkgName: string | ||
): SavedObjectToBe { | ||
// convert that to an object | ||
const asset = changeAssetIds(jsonAsset, pkgName); | ||
|
||
return { | ||
type: asset.type, | ||
id: asset.id, | ||
attributes: asset.attributes, | ||
references: asset.references || [], | ||
migrationVersion: asset.migrationVersion || {}, | ||
}; | ||
} | ||
|
||
// modifies id property and the id property of references objects (not index-pattern) | ||
// to be prepended with the package name to distinguish assets from Beats modules' assets | ||
export const changeAssetIds = (asset: ArchiveAsset, pkgName: string): ArchiveAsset => { | ||
const references = asset.references.map((ref) => { | ||
if (ref.type === KibanaAssetType.indexPattern) return ref; | ||
const id = getAssetId(ref.id, pkgName); | ||
return { ...ref, id }; | ||
}); | ||
return { | ||
...asset, | ||
id: getAssetId(asset.id, pkgName), | ||
references, | ||
}; | ||
}; | ||
|
||
export const getAssetId = (id: string, pkgName: string) => { | ||
return `${pkgName}-${id}`; | ||
}; | ||
|
||
// TODO: make it an exhaustive list | ||
// e.g. switch statement with cases for each enum key returning `never` for default case | ||
export async function installKibanaAssets(options: { | ||
savedObjectsClient: SavedObjectsClientContract; | ||
pkgName: string; | ||
paths: string[]; | ||
}) { | ||
const { savedObjectsClient, paths, pkgName } = options; | ||
|
||
// Only install Kibana assets during package installation. | ||
const kibanaAssetTypes = Object.values(KibanaAssetType); | ||
const installationPromises = kibanaAssetTypes.map((assetType) => | ||
installKibanaSavedObjects({ savedObjectsClient, assetType, paths, pkgName }) | ||
); | ||
|
||
// installKibanaSavedObjects returns AssetReference[], so .map creates AssetReference[][] | ||
// call .flat to flatten into one dimensional array | ||
return Promise.all(installationPromises).then((results) => results.flat()); | ||
} | ||
|
||
async function installKibanaSavedObjects({ | ||
savedObjectsClient, | ||
assetType, | ||
paths, | ||
pkgName, | ||
}: { | ||
savedObjectsClient: SavedObjectsClientContract; | ||
assetType: KibanaAssetType; | ||
paths: string[]; | ||
pkgName: string; | ||
}) { | ||
const isSameType = (path: string) => assetType === Registry.pathParts(path).type; | ||
const pathsOfType = paths.filter((path) => isSameType(path)); | ||
const kibanaAssets = await Promise.all(pathsOfType.map((path) => getKibanaAsset(path))); | ||
const toBeSavedObjects = await Promise.all( | ||
kibanaAssets.map((asset) => createSavedObjectKibanaAsset(asset, pkgName)) | ||
); | ||
|
||
if (toBeSavedObjects.length === 0) { | ||
return []; | ||
} else { | ||
const createResults = await savedObjectsClient.bulkCreate(toBeSavedObjects, { | ||
overwrite: true, | ||
}); | ||
const createdObjects = createResults.saved_objects; | ||
const installed = createdObjects.map(toAssetReference); | ||
return installed; | ||
} | ||
} | ||
|
||
function toAssetReference({ id, type }: SavedObject) { | ||
const reference: AssetReference = { id, type: type as KibanaAssetType }; | ||
|
||
return reference; | ||
} |
133 changes: 133 additions & 0 deletions
133
...ingest_manager/server/services/epm/kibana/assets/tests/__snapshots__/install.test.ts.snap
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
129 changes: 129 additions & 0 deletions
129
x-pack/plugins/ingest_manager/server/services/epm/kibana/assets/tests/dashboard.json
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,129 @@ | ||
{ | ||
"attributes": { | ||
"description": "Overview dashboard for the Nginx integration in Metrics", | ||
"hits": 0, | ||
"kibanaSavedObjectMeta": { | ||
"searchSourceJSON": { | ||
"filter": [], | ||
"highlightAll": true, | ||
"query": { | ||
"language": "kuery", | ||
"query": "" | ||
}, | ||
"version": true | ||
} | ||
}, | ||
"optionsJSON": { | ||
"darkTheme": false, | ||
"hidePanelTitles": false, | ||
"useMargins": true | ||
}, | ||
"panelsJSON": [ | ||
{ | ||
"embeddableConfig": {}, | ||
"gridData": { | ||
"h": 12, | ||
"i": "1", | ||
"w": 24, | ||
"x": 24, | ||
"y": 0 | ||
}, | ||
"panelIndex": "1", | ||
"panelRefName": "panel_0", | ||
"version": "7.3.0" | ||
}, | ||
{ | ||
"embeddableConfig": {}, | ||
"gridData": { | ||
"h": 12, | ||
"i": "2", | ||
"w": 24, | ||
"x": 24, | ||
"y": 12 | ||
}, | ||
"panelIndex": "2", | ||
"panelRefName": "panel_1", | ||
"version": "7.3.0" | ||
}, | ||
{ | ||
"embeddableConfig": {}, | ||
"gridData": { | ||
"h": 12, | ||
"i": "3", | ||
"w": 24, | ||
"x": 0, | ||
"y": 12 | ||
}, | ||
"panelIndex": "3", | ||
"panelRefName": "panel_2", | ||
"version": "7.3.0" | ||
}, | ||
{ | ||
"embeddableConfig": {}, | ||
"gridData": { | ||
"h": 12, | ||
"i": "4", | ||
"w": 24, | ||
"x": 0, | ||
"y": 0 | ||
}, | ||
"panelIndex": "4", | ||
"panelRefName": "panel_3", | ||
"version": "7.3.0" | ||
}, | ||
{ | ||
"embeddableConfig": {}, | ||
"gridData": { | ||
"h": 12, | ||
"i": "5", | ||
"w": 48, | ||
"x": 0, | ||
"y": 24 | ||
}, | ||
"panelIndex": "5", | ||
"panelRefName": "panel_4", | ||
"version": "7.3.0" | ||
} | ||
], | ||
"timeRestore": false, | ||
"title": "[Metrics Nginx] Overview ECS", | ||
"version": 1 | ||
}, | ||
"id": "023d2930-f1a5-11e7-a9ef-93c69af7b129-ecs", | ||
"migrationVersion": { | ||
"dashboard": "7.3.0" | ||
}, | ||
"references": [ | ||
{ | ||
"id": "metrics-*", | ||
"name": "kibanaSavedObjectMeta.searchSourceJSON.filter[0].meta.index", | ||
"type": "index-pattern" | ||
}, | ||
{ | ||
"id": "555df8a0-f1a1-11e7-a9ef-93c69af7b129-ecs", | ||
"name": "panel_0", | ||
"type": "search" | ||
}, | ||
{ | ||
"id": "a1d92240-f1a1-11e7-a9ef-93c69af7b129-ecs", | ||
"name": "panel_1", | ||
"type": "map" | ||
}, | ||
{ | ||
"id": "d763a570-f1a1-11e7-a9ef-93c69af7b129-ecs", | ||
"name": "panel_2", | ||
"type": "dashboard" | ||
}, | ||
{ | ||
"id": "47a8e0f0-f1a4-11e7-a9ef-93c69af7b129-ecs", | ||
"name": "panel_3", | ||
"type": "visualization" | ||
}, | ||
{ | ||
"id": "dcbffe30-f1a4-11e7-a9ef-93c69af7b129-ecs", | ||
"name": "panel_4", | ||
"type": "visualization" | ||
} | ||
], | ||
"type": "dashboard" | ||
} |
Oops, something went wrong.