Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[Discover] One Discover context awareness (#183797)
## Summary This PR includes the initial implementation of the Discover contextual awareness framework and composable profiles: ![logs_table](https://github.com/elastic/kibana/assets/25592674/0815687a-c4d8-4a80-8f67-5e1de0c65adf) ### Context We currently support three levels of context in Discover: - Root context: - Based on the current solution type, navigational parameters, etc. - Resolved at application initialization and on parameter changes. - Runs synchronously or asynchronously. - Data source context: - Based on the current ES|QL query or data view. - Resolved on ES|QL query or data view change, before data fetching occurs. - Runs synchronously or asynchronously. - Document context: - Based on individual ES|QL records or ES documents. - Resolved individually for each ES|QL record or ES document after data fetching runs. - Runs synchronously only. ### Composable profiles To support application extensibility based on context, we've introduced the concept of "composable profiles". Composable profiles are implementations of a core `Profile` interface (or a subset of it) containing all of the available extension points Discover supports. A composable profile can be implemented at any context level through a "profile provider", responsible for defining the composable profile and its associated context resolution method. The context resolution method, named `resolve`, determines if its composable profile is a match for the current Discover context, and returns related metadata in a `context` object. ### Merged accessors Composable profiles operate similarly to middleware in that each of their extension point implementations are passed a `prev` argument, which can be called to access the results from profiles at previous context levels, and allows overwriting or composing a final result from the previous results. The method Discover calls to trigger the extension point merging process and obtain a final result from the combined profiles is referred to as a "merged accessor". The following diagram illustrates the extension point merging process: ![image](https://github.com/davismcphee/kibana/assets/25592674/59f7cd23-c1e0-4d8e-99ed-02460211ed96) ### Supporting services The contextual awareness framework is driven by two main supporting services called `ProfileService` and `ProfilesManager`. Each context level has a dedicated profile service, e.g. `RootProfileService`, which is responsible for accepting profile provider registrations and running through each provider in order during context resolution to identify a matching profile. A single `ProfilesManager` is instantiated on Discover load, or one per saved search panel in a dashboard. The profiles manager is responsible for the following: - Managing state associated with the current Discover context. - Coordinating profile services and exposing resolution methods for each context level. - Providing access to the combined set of resolved profiles. - Deduplicating profile resolution attempts with identical parameters. - Error handling and fallback behaviour on profile resolution failure. ### Bringing it all together The following diagram models the overall Discover contextual awareness framework and how each of the above concepts come together: ![image](https://github.com/elastic/kibana/assets/25592674/49193141-c50a-473f-9d38-eb09fbaaffbe) ### Followup work - We'll want to add developer documentation as a followup, which I've created an issue for here: #184698. The summary for this PR can be used as the basis for the documentation. - Since we currently have no profile or extension point implementations, this PR does not include any functional tests. We should create example implementations for functional testing and ensure they're only enabled when running the test suite or when developers want them enabled. I've created a followup issue for this work here: #184699. ### Testing notes Testing the framework is tricky since we have no actual profile or extension point implementations yet. However, I previously added example implementations that I was using for testing while building the framework. I've removed the example implementations so they don't get merged, but they can be temporarily restored for testing by reverting the commit where I removed them: `git revert 5752651`. You'll also need to uncomment the following lines in `src/plugins/discover/public/plugin.tsx`: https://github.com/elastic/kibana/blob/ce85a6a35fa3623bfdfac7dae41df2d840394154/src/plugins/discover/public/plugin.tsx#L458-L463 To test the root profile resolution based on solution type, I'd recommend enabling the solution nav locally by adding the following to `kibana.dev.yml`: ```yml xpack.cloud_integrations.experiments.enabled: true xpack.cloud_integrations.experiments.flag_overrides: "solutionNavEnabled": true xpack.cloud.id: "ftr_fake_cloud_id:aGVsbG8uY29tOjQ0MyRFUzEyM2FiYyRrYm4xMjNhYmM=" xpack.cloud.base_url: "https://cloud.elastic.co" xpack.cloud.deployment_url: "/deployments/deploymentId" ``` In order to change the active solution type, modify the `mockSpaceState` in `src/plugins/navigation/public/plugin.tsx`: https://github.com/elastic/kibana/blob/79e51d64f83da6af56107a633a5a3b49947f1ebe/src/plugins/navigation/public/plugin.tsx#L159-L162 For test data, I'd recommend running the following commands to generate sample ECS compliant logs and metrics data: ``` node scripts/synthtrace.js --target "http://elastic:changeme@localhost:9200/" --kibana "http://elastic:changeme@localhost:5601/" --live --logLevel debug simple_logs.ts node scripts/synthtrace.js --target "http://elastic:changeme@localhost:9200/" --kibana "http://elastic:changeme@localhost:5601/" --live --logLevel debug simple_trace.ts ``` And lastly a couple of the ES|QL queries I used for testing: ``` // resolves to the example logs data source context from logs-synth-default // mixed dataset that falls back to vanilla Discover // helpful for testing document context in the doc viewer flyout from logs-synth-default,metrics-* ``` Resolves #181962. ### Checklist - [ ] Any text added follows [EUI's writing guidelines](https://elastic.github.io/eui/#/guidelines/writing), uses sentence case text and includes [i18n support](https://github.com/elastic/kibana/blob/main/packages/kbn-i18n/README.md) - [ ] [Documentation](https://www.elastic.co/guide/en/kibana/master/development-documentation.html) was added for features that require explanation or tutorials - [x] [Unit or functional tests](https://www.elastic.co/guide/en/kibana/master/development-tests.html) were updated or added to match the most common scenarios - [ ] [Flaky Test Runner](https://ci-stats.kibana.dev/trigger_flaky_test_runner/1) was used on any tests changed - [ ] Any UI touched in this PR is usable by keyboard only (learn more about [keyboard accessibility](https://webaim.org/techniques/keyboard/)) - [ ] Any UI touched in this PR does not create any new axe failures (run axe in browser: [FF](https://addons.mozilla.org/en-US/firefox/addon/axe-devtools/), [Chrome](https://chrome.google.com/webstore/detail/axe-web-accessibility-tes/lhdoppojpmngadmnindnejefpokejbdd?hl=en-US)) - [ ] If a plugin configuration key changed, check if it needs to be allowlisted in the cloud and added to the [docker list](https://github.com/elastic/kibana/blob/main/src/dev/build/tasks/os_packages/docker_generator/resources/base/bin/kibana-docker) - [ ] This renders correctly on smaller devices using a responsive layout. (You can test this [in your browser](https://www.browserstack.com/guide/responsive-testing-on-local-server)) - [ ] This was checked for [cross-browser compatibility](https://www.elastic.co/support/matrix#matrix_browsers) ### For maintainers - [ ] This was checked for breaking API changes and was [labeled appropriately](https://www.elastic.co/guide/en/kibana/master/contributing.html#kibana-release-notes-process) --------- Co-authored-by: kibanamachine <42973632+kibanamachine@users.noreply.github.com>