Skip to content
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

[Performance][Security Solution][2/4] - Timeline Performance #212478

Merged
merged 6 commits into from
Mar 11, 2025

Conversation

michaelolo24
Copy link
Contributor

@michaelolo24 michaelolo24 commented Feb 26, 2025

Summary

Part 2 of #212173

Testing

For setup see testing section here: #212173 (comment)

Areas/How to test:

  • For the following pages, test there are no fields api requests in the inspector network tab when visiting from another page. IF YOU REFRESH on any of these pages, you will see these requests as they are called by the Query Search Bar and the useInitSourcerer call
    • Cases Page
    • Dashboard Page
    • Timelines Page
  • Timeline
    • All Tabs
      • Does it show the loading screen on first interaction?
      • Does the fields api fire on first interaction with the tab
      • When you navigate back to those tabs, do they not re-render?
  • All other pages hosting timeline
  • Do you feel like the performance is generally better?

Background

When investigating the performance of the security solution application, one of the issues that was observed was queries to the fields api on pages that had no reason making that request (such as Cases, or the Dashboards list view). This was due to the background background loaded tabs of timeline loading the relevant dataView necessary for their search functionality. When the fields request is significantly large this can have a massive impact on the experience of users on pages that should be relatively responsive.

To fix this a few changes were made.

  1. First the withDataView HOC was removed as it was only used in 2 components that shared a parent - child relationship, and the child UnifiedTimeline was only used in the parent. The hook that HOC calls was not caching the dataView being created, so dataView.create was being called up to 6 times unnecessarily. Now it is only called once in each tab.

  2. A new wrapper OnDemandRenderer (open to different naming 😅) was created that will not render any of the nested tabs until they are opened. Once they are opened, they stay in memory, to avoid re-calling expensive api's every time a user switches tabs.
    Note: There is currently a known issue where navigating between various routes in security solution causes the whole application to unmount and re-mount. Which means every page change will lead to timeline needing to be re-loaded when the tab is opened. This is being resolved in a separate effort.

  3. Additional checks were added to the useTimelineEvents hook to limit additional re-renders caused by unnecessary reference changes when the underlying values never actually change

Checklist

Check the PR satisfies following conditions.

Reviewers should verify this PR satisfies this list as well.

Identify risks

@michaelolo24 michaelolo24 added release_note:skip Skip the PR/issue when compiling release notes v9.0.0 Team:Threat Hunting:Investigations Security Solution Investigations Team backport:all-open Backport to all branches that could still receive a release v9.1.0 v8.19.0 v8.17.3 labels Feb 26, 2025
@michaelolo24 michaelolo24 force-pushed the security-performance-timeline branch from 222a79a to 594807c Compare February 26, 2025 15:51
@michaelolo24 michaelolo24 marked this pull request as ready for review February 26, 2025 16:17
@michaelolo24 michaelolo24 requested a review from a team as a code owner February 26, 2025 16:17
@elasticmachine
Copy link
Contributor

Pinging @elastic/security-threat-hunting-investigations (Team:Threat Hunting:Investigations)

@michaelolo24 michaelolo24 force-pushed the security-performance-timeline branch from 2576a0c to c358526 Compare March 6, 2025 12:50
Copy link
Contributor

@logeekal logeekal left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done code review as of now. Will post the results of Desk Testing soon.

loadNextBatch,
refreshedAt: 0,
});
setTimelineResponse(defaultTimelineResponse);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@@ -529,6 +522,8 @@ export const useTimelineEventsHandler = ({
return [loading, finalTimelineLineResponse, timelineSearchHandler];
};

const defaultEvents: TimelineItem[][] = [];
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

might result in error somewhere since it is a 2D array and previously eventsPerPage[0] was [] and with this change it is undefined

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's only accessed on line 597, which would only be doing empty work to flatten a nested empty array. Happy to revert it, but not sure if it's necessary


OnDemandRenderer.displayName = 'OnDemandRenderer';

export const OnDemandSuspenseFallback = () => (
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Since this component is not in itself related to React.suspense, I would suggest renaming it to TimelineTabFallback

timerangeKind,
});

useEffect(() => {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you think we need to remove similar useEffect in query and eql tab so there it does not override the effect of this useEffect 🤷

Copy link
Contributor Author

@michaelolo24 michaelolo24 Mar 6, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Potentially, but it should be aligned with the query tab as they should be running the same query string. I don't expect this change to be necessary

@@ -65,7 +65,7 @@ export const TimelineBottomBar = React.memo<TimelineBottomBarProps>(
</EuiFlexItem>
{!show && ( // this is a hack because TimelineEventsCountBadge is using react-reverse-portal so the component which is used in multiple places cannot be visible in multiple places at the same time
<EuiFlexItem grow={false} data-test-subj="timeline-event-count-badge">
<TimelineEventsCountBadge />
<TimelineQueryTabEventsCount timelineId={timelineId} />
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are you planning to remove that OutPortal InPortal stuff as well in this PR?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, I wasn't planning on making that change in this PR

@michaelolo24 michaelolo24 force-pushed the security-performance-timeline branch 2 times, most recently from 7536190 to e3c8e54 Compare March 6, 2025 20:03
Copy link
Contributor

@logeekal logeekal left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Desk Testing looks good. Below are couple of observations:

Timeline Search Strategy firing twice

When there is a timeline bottom bar, timelineSearchStrategy is firing twice to get the count of events, everytime. See demo below:

timelineSearchStrategy_firing_twice.mp4

App Perf with 500K total fields

I tried app performance with 500K total fields with :

  • one document having all 500K fields populated
  • around 10K docs with 25K fields populated

the whole app feels slow specially because useInitSourcerer takes around 10s to finish and get all the fields when visiting Alerts Page. a

Below URL took 12s to resolve and that essential blocks whole Alerts page. And app also seems slow. Not sure why.

image

http://localhost:5601/internal/data_views/fields?pattern=.alerts-security.alerts-default%2Capm-*-transaction*%2Cauditbeat-*%2Cendgame-*%2Cfilebeat-*%2Clogs-*%2Cpacketbeat-*%2Ctest*%2Ctraces-apm*%2Cwinlogbeat-*%2C-*elastic-cloud-logs-*&meta_fields=_source&meta_fields=_id&meta_fields=_index&meta_fields=_score&meta_fields=_ignored&allow_no_index=true&apiVersion=1

Screen.Recording.2025-03-07.at.12.31.40.mov

@logeekal
Copy link
Contributor

logeekal commented Mar 7, 2025

One more feedback. it looks like this PR introduces a wierd space in timeline as highlighted below. for comparison, i have posted a screenshot from Release-sec instance.

Screenshot 2025-03-07 at 13 42 58 Screenshot 2025-03-07 at 13 45 54

@michaelolo24 michaelolo24 added ci:cloud-deploy Create or update a Cloud deployment ci:project-redeploy Always create a new Cloud project labels Mar 7, 2025
@michaelolo24
Copy link
Contributor Author

@logeekal - Can you retest, I was unable to replicate the duplicate queries...and the gap is from the borealis changes as that is also currently on main, but not 8.18

@michaelolo24 michaelolo24 force-pushed the security-performance-timeline branch from d1c290b to c81c4a5 Compare March 10, 2025 13:07
@elasticmachine
Copy link
Contributor

elasticmachine commented Mar 10, 2025

💛 Build succeeded, but was flaky

Failed CI Steps

Test Failures

  • [job] [logs] Detection Engine - Security Solution Cypress Tests #5 / Custom query rules Custom detection rules creation with data views Creates and enables a new rule Creates and enables a new rule

Metrics [docs]

Module Count

Fewer modules leads to a faster build time

id before after diff
securitySolution 7062 7064 +2

Async chunks

Total size of all lazy-loaded chunks that will be downloaded as the user navigates the app

id before after diff
securitySolution 8.9MB 8.8MB -13.2KB

Page load bundle

Size of the bundles that are downloaded on every page load. Target size is below 100kb

id before after diff
securitySolution 87.5KB 87.5KB -9.0B

History

  • 💛 Build #281813 was flaky d1c290b1d285f514e1ac244268420b3bf16602ef
  • 💚 Build #281587 succeeded e3c8e54bd0c0b1cead00bd56e5e4129916864ab8
  • 💔 Build #281555 failed 7536190dd72c3809274348e835919415b42379ca
  • 💔 Build #281399 failed c3585261c3e9fb16a9c345d7c245f0f6c23a0a39

Copy link
Contributor

@logeekal logeekal left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you retest, I was unable to replicate the duplicate queries...and the gap is from the borealis changes as that is also currently on main, but not 8.18

@michaelolo24 , I retested and can confirm that now only single query is firing. I also noticed that gap is only in light theme and not in borealis 🤦 .

Thanks for making these changes.

@michaelolo24 michaelolo24 added the backport:version Backport to applied version labels label Mar 11, 2025
@michaelolo24 michaelolo24 merged commit 2d8f3c1 into elastic:main Mar 11, 2025
19 checks passed
@kibanamachine
Copy link
Contributor

Starting backport for target branches: 8.17, 8.x

https://github.com/elastic/kibana/actions/runs/13793767412

kibanamachine pushed a commit to kibanamachine/kibana that referenced this pull request Mar 11, 2025
…#212478)

## Summary
Part 2 of elastic#212173

### Testing
For setup see testing section here:
elastic#212173 (comment)

**Areas/How to test:**
- For the following pages, test there are no `fields` api requests in
the inspector network tab when visiting from another page. IF YOU
REFRESH on any of these pages, you will see these requests as they are
called by the Query Search Bar and the `useInitSourcerer` call
  - Cases Page
  - Dashboard Page
  - Timelines Page
- Timeline
  - All Tabs
    - Does it show the loading screen on first interaction?
    - Does the `fields` api fire on first interaction with the tab
    - When you navigate back to those tabs, do they not re-render?
- All other pages hosting timeline
 - Do you feel like the performance is generally better?

### Background

When investigating the performance of the security solution application,
one of the issues that was observed was queries to the `fields` api on
pages that had no reason making that request (such as Cases, or the
Dashboards list view). This was due to the background background loaded
tabs of timeline loading the relevant `dataView` necessary for their
search functionality. When the fields request is significantly large
this can have a massive impact on the experience of users on pages that
should be relatively responsive.

To fix this a few changes were made.

1. First the `withDataView` HOC was removed as it was only used in 2
components that shared a parent - child relationship, and the child
`UnifiedTimeline` was only used in the parent. The hook that HOC calls
was not caching the dataView being created, so `dataView.create` was
being called up to 6 times unnecessarily. Now it is only called once in
each tab.

2. A new wrapper `OnDemandRenderer` (open to different naming 😅) was
created that will not render any of the nested tabs until they are
opened. Once they are opened, they stay in memory, to avoid re-calling
expensive api's every time a user switches tabs.
_Note_: There is currently a known issue where navigating between
various routes in security solution causes the whole application to
unmount and re-mount. Which means every page change will lead to
timeline needing to be re-loaded when the tab is opened. This is being
resolved in a separate effort.

3. Additional checks were added to the `useTimelineEvents` hook to limit
additional re-renders caused by unnecessary reference changes when the
underlying values never actually change

### Checklist

Check the PR satisfies following conditions.

Reviewers should verify this PR satisfies this list as well.

- [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
### Identify risks

(cherry picked from commit 2d8f3c1)
@kibanamachine
Copy link
Contributor

💔 Some backports could not be created

Status Branch Result
8.17 Backport failed because of merge conflicts
8.x

Note: Successful backport PRs will be merged automatically after passing CI.

Manual backport

To create the backport manually run:

node scripts/backport --pr 212478

Questions ?

Please refer to the Backport tool documentation

michaelolo24 added a commit to michaelolo24/kibana that referenced this pull request Mar 11, 2025
…#212478)

## Summary
Part 2 of elastic#212173

### Testing
For setup see testing section here:
elastic#212173 (comment)

**Areas/How to test:**
- For the following pages, test there are no `fields` api requests in
the inspector network tab when visiting from another page. IF YOU
REFRESH on any of these pages, you will see these requests as they are
called by the Query Search Bar and the `useInitSourcerer` call
  - Cases Page
  - Dashboard Page
  - Timelines Page
- Timeline
  - All Tabs
    - Does it show the loading screen on first interaction?
    - Does the `fields` api fire on first interaction with the tab
    - When you navigate back to those tabs, do they not re-render?
- All other pages hosting timeline
 - Do you feel like the performance is generally better?

### Background

When investigating the performance of the security solution application,
one of the issues that was observed was queries to the `fields` api on
pages that had no reason making that request (such as Cases, or the
Dashboards list view). This was due to the background background loaded
tabs of timeline loading the relevant `dataView` necessary for their
search functionality. When the fields request is significantly large
this can have a massive impact on the experience of users on pages that
should be relatively responsive.

To fix this a few changes were made.

1. First the `withDataView` HOC was removed as it was only used in 2
components that shared a parent - child relationship, and the child
`UnifiedTimeline` was only used in the parent. The hook that HOC calls
was not caching the dataView being created, so `dataView.create` was
being called up to 6 times unnecessarily. Now it is only called once in
each tab.

2. A new wrapper `OnDemandRenderer` (open to different naming 😅) was
created that will not render any of the nested tabs until they are
opened. Once they are opened, they stay in memory, to avoid re-calling
expensive api's every time a user switches tabs.
_Note_: There is currently a known issue where navigating between
various routes in security solution causes the whole application to
unmount and re-mount. Which means every page change will lead to
timeline needing to be re-loaded when the tab is opened. This is being
resolved in a separate effort.

3. Additional checks were added to the `useTimelineEvents` hook to limit
additional re-renders caused by unnecessary reference changes when the
underlying values never actually change

### Checklist

Check the PR satisfies following conditions.

Reviewers should verify this PR satisfies this list as well.

- [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
### Identify risks

(cherry picked from commit 2d8f3c1)

# Conflicts:
#	x-pack/plugins/security_solution/public/timelines/components/timeline/context.ts
#	x-pack/plugins/security_solution/public/timelines/components/timeline/index.tsx
#	x-pack/plugins/security_solution/public/timelines/components/timeline/tabs/index.tsx
#	x-pack/plugins/security_solution/public/timelines/components/timeline/tabs/lazy_timeline_tab_renderer.test.tsx
#	x-pack/plugins/security_solution/public/timelines/components/timeline/tabs/lazy_timeline_tab_renderer.tsx
#	x-pack/plugins/security_solution/public/timelines/components/timeline/tabs/query/events_count.tsx
#	x-pack/plugins/security_solution/public/timelines/components/timeline/unified_components/index.tsx
@michaelolo24
Copy link
Contributor Author

💚 All backports created successfully

Status Branch Result
8.17

Note: Successful backport PRs will be merged automatically after passing CI.

Questions ?

Please refer to the Backport tool documentation

@kibanamachine kibanamachine added the backport missing Added to PRs automatically when the are determined to be missing a backport. label Mar 13, 2025
@kibanamachine
Copy link
Contributor

Looks like this PR has backport PRs but they still haven't been merged. Please merge them ASAP to keep the branches relatively in sync.

4 similar comments
@kibanamachine
Copy link
Contributor

Looks like this PR has backport PRs but they still haven't been merged. Please merge them ASAP to keep the branches relatively in sync.

@kibanamachine
Copy link
Contributor

Looks like this PR has backport PRs but they still haven't been merged. Please merge them ASAP to keep the branches relatively in sync.

@kibanamachine
Copy link
Contributor

Looks like this PR has backport PRs but they still haven't been merged. Please merge them ASAP to keep the branches relatively in sync.

@kibanamachine
Copy link
Contributor

Looks like this PR has backport PRs but they still haven't been merged. Please merge them ASAP to keep the branches relatively in sync.

michaelolo24 added a commit that referenced this pull request Mar 20, 2025
…212478) (#213988)

# Backport

This will backport the following commits from `main` to `8.17`:
- [[Performance][Security Solution][2/4] - Timeline Performance
(#212478)](#212478)

<!--- Backport version: 9.6.6 -->

### Questions ?
Please refer to the [Backport tool
documentation](https://github.com/sorenlouv/backport)

<!--BACKPORT [{"author":{"name":"Michael
Olorunnisola","email":"[email protected]"},"sourceCommit":{"committedDate":"2025-03-11T16:56:45Z","message":"[Performance][Security
Solution][2/4] - Timeline Performance (#212478)\n\n## Summary\nPart 2 of
https://github.com/elastic/kibana/pull/212173\n\n### Testing\nFor setup
see testing section
here:\nhttps://github.com//pull/212173#issue-2870522020\n\n**Areas/How
to test:**\n- For the following pages, test there are no `fields` api
requests in\nthe inspector network tab when visiting from another page.
IF YOU\nREFRESH on any of these pages, you will see these requests as
they are\ncalled by the Query Search Bar and the `useInitSourcerer`
call\n - Cases Page\n - Dashboard Page\n - Timelines Page\n- Timeline\n
- All Tabs\n - Does it show the loading screen on first interaction?\n -
Does the `fields` api fire on first interaction with the tab\n - When
you navigate back to those tabs, do they not re-render?\n- All other
pages hosting timeline\n - Do you feel like the performance is generally
better?\n\n\n### Background\n\nWhen investigating the performance of the
security solution application,\none of the issues that was observed was
queries to the `fields` api on\npages that had no reason making that
request (such as Cases, or the\nDashboards list view). This was due to
the background background loaded\ntabs of timeline loading the relevant
`dataView` necessary for their\nsearch functionality. When the fields
request is significantly large\nthis can have a massive impact on the
experience of users on pages that\nshould be relatively
responsive.\n\nTo fix this a few changes were made. \n\n1. First the
`withDataView` HOC was removed as it was only used in 2\ncomponents that
shared a parent - child relationship, and the child\n`UnifiedTimeline`
was only used in the parent. The hook that HOC calls\nwas not caching
the dataView being created, so `dataView.create` was\nbeing called up to
6 times unnecessarily. Now it is only called once in\neach tab.\n\n2. A
new wrapper `OnDemandRenderer` (open to different naming 😅) was\ncreated
that will not render any of the nested tabs until they are\nopened. Once
they are opened, they stay in memory, to avoid re-calling\nexpensive
api's every time a user switches tabs.\n_Note_: There is currently a
known issue where navigating between\nvarious routes in security
solution causes the whole application to\nunmount and re-mount. Which
means every page change will lead to\ntimeline needing to be re-loaded
when the tab is opened. This is being\nresolved in a separate
effort.\n\n3. Additional checks were added to the `useTimelineEvents`
hook to limit\nadditional re-renders caused by unnecessary reference
changes when the\nunderlying values never actually change\n\n###
Checklist\n\nCheck the PR satisfies following conditions. \n\nReviewers
should verify this PR satisfies this list as well.\n\n- [x] [Unit or
functional\ntests](https://www.elastic.co/guide/en/kibana/master/development-tests.html)\nwere
updated or added to match the most common scenarios\n### Identify
risks","sha":"2d8f3c1544aa6bff74623273a278f580df0d918d","branchLabelMapping":{"^v9.1.0$":"main","^v8.19.0$":"8.x","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:skip","Team:Threat
Hunting:Investigations","ci:cloud-deploy","ci:project-redeploy","backport:version","v9.1.0","v8.19.0","v8.17.4"],"title":"[Performance][Security
Solution][2/4] - Timeline
Performance","number":212478,"url":"https://github.com/elastic/kibana/pull/212478","mergeCommit":{"message":"[Performance][Security
Solution][2/4] - Timeline Performance (#212478)\n\n## Summary\nPart 2 of
https://github.com/elastic/kibana/pull/212173\n\n### Testing\nFor setup
see testing section
here:\nhttps://github.com//pull/212173#issue-2870522020\n\n**Areas/How
to test:**\n- For the following pages, test there are no `fields` api
requests in\nthe inspector network tab when visiting from another page.
IF YOU\nREFRESH on any of these pages, you will see these requests as
they are\ncalled by the Query Search Bar and the `useInitSourcerer`
call\n - Cases Page\n - Dashboard Page\n - Timelines Page\n- Timeline\n
- All Tabs\n - Does it show the loading screen on first interaction?\n -
Does the `fields` api fire on first interaction with the tab\n - When
you navigate back to those tabs, do they not re-render?\n- All other
pages hosting timeline\n - Do you feel like the performance is generally
better?\n\n\n### Background\n\nWhen investigating the performance of the
security solution application,\none of the issues that was observed was
queries to the `fields` api on\npages that had no reason making that
request (such as Cases, or the\nDashboards list view). This was due to
the background background loaded\ntabs of timeline loading the relevant
`dataView` necessary for their\nsearch functionality. When the fields
request is significantly large\nthis can have a massive impact on the
experience of users on pages that\nshould be relatively
responsive.\n\nTo fix this a few changes were made. \n\n1. First the
`withDataView` HOC was removed as it was only used in 2\ncomponents that
shared a parent - child relationship, and the child\n`UnifiedTimeline`
was only used in the parent. The hook that HOC calls\nwas not caching
the dataView being created, so `dataView.create` was\nbeing called up to
6 times unnecessarily. Now it is only called once in\neach tab.\n\n2. A
new wrapper `OnDemandRenderer` (open to different naming 😅) was\ncreated
that will not render any of the nested tabs until they are\nopened. Once
they are opened, they stay in memory, to avoid re-calling\nexpensive
api's every time a user switches tabs.\n_Note_: There is currently a
known issue where navigating between\nvarious routes in security
solution causes the whole application to\nunmount and re-mount. Which
means every page change will lead to\ntimeline needing to be re-loaded
when the tab is opened. This is being\nresolved in a separate
effort.\n\n3. Additional checks were added to the `useTimelineEvents`
hook to limit\nadditional re-renders caused by unnecessary reference
changes when the\nunderlying values never actually change\n\n###
Checklist\n\nCheck the PR satisfies following conditions. \n\nReviewers
should verify this PR satisfies this list as well.\n\n- [x] [Unit or
functional\ntests](https://www.elastic.co/guide/en/kibana/master/development-tests.html)\nwere
updated or added to match the most common scenarios\n### Identify
risks","sha":"2d8f3c1544aa6bff74623273a278f580df0d918d"}},"sourceBranch":"main","suggestedTargetBranches":["8.17"],"targetPullRequestStates":[{"branch":"main","label":"v9.1.0","branchLabelMappingKey":"^v9.1.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/212478","number":212478,"mergeCommit":{"message":"[Performance][Security
Solution][2/4] - Timeline Performance (#212478)\n\n## Summary\nPart 2 of
https://github.com/elastic/kibana/pull/212173\n\n### Testing\nFor setup
see testing section
here:\nhttps://github.com//pull/212173#issue-2870522020\n\n**Areas/How
to test:**\n- For the following pages, test there are no `fields` api
requests in\nthe inspector network tab when visiting from another page.
IF YOU\nREFRESH on any of these pages, you will see these requests as
they are\ncalled by the Query Search Bar and the `useInitSourcerer`
call\n - Cases Page\n - Dashboard Page\n - Timelines Page\n- Timeline\n
- All Tabs\n - Does it show the loading screen on first interaction?\n -
Does the `fields` api fire on first interaction with the tab\n - When
you navigate back to those tabs, do they not re-render?\n- All other
pages hosting timeline\n - Do you feel like the performance is generally
better?\n\n\n### Background\n\nWhen investigating the performance of the
security solution application,\none of the issues that was observed was
queries to the `fields` api on\npages that had no reason making that
request (such as Cases, or the\nDashboards list view). This was due to
the background background loaded\ntabs of timeline loading the relevant
`dataView` necessary for their\nsearch functionality. When the fields
request is significantly large\nthis can have a massive impact on the
experience of users on pages that\nshould be relatively
responsive.\n\nTo fix this a few changes were made. \n\n1. First the
`withDataView` HOC was removed as it was only used in 2\ncomponents that
shared a parent - child relationship, and the child\n`UnifiedTimeline`
was only used in the parent. The hook that HOC calls\nwas not caching
the dataView being created, so `dataView.create` was\nbeing called up to
6 times unnecessarily. Now it is only called once in\neach tab.\n\n2. A
new wrapper `OnDemandRenderer` (open to different naming 😅) was\ncreated
that will not render any of the nested tabs until they are\nopened. Once
they are opened, they stay in memory, to avoid re-calling\nexpensive
api's every time a user switches tabs.\n_Note_: There is currently a
known issue where navigating between\nvarious routes in security
solution causes the whole application to\nunmount and re-mount. Which
means every page change will lead to\ntimeline needing to be re-loaded
when the tab is opened. This is being\nresolved in a separate
effort.\n\n3. Additional checks were added to the `useTimelineEvents`
hook to limit\nadditional re-renders caused by unnecessary reference
changes when the\nunderlying values never actually change\n\n###
Checklist\n\nCheck the PR satisfies following conditions. \n\nReviewers
should verify this PR satisfies this list as well.\n\n- [x] [Unit or
functional\ntests](https://www.elastic.co/guide/en/kibana/master/development-tests.html)\nwere
updated or added to match the most common scenarios\n### Identify
risks","sha":"2d8f3c1544aa6bff74623273a278f580df0d918d"}},{"branch":"8.x","label":"v8.19.0","branchLabelMappingKey":"^v8.19.0$","isSourceBranch":false,"url":"https://github.com/elastic/kibana/pull/213978","number":213978,"state":"OPEN"},{"branch":"8.17","label":"v8.17.4","branchLabelMappingKey":"^v(\\d+).(\\d+).\\d+$","isSourceBranch":false,"state":"NOT_CREATED"}]}]
BACKPORT-->
@kibanamachine
Copy link
Contributor

Looks like this PR has backport PRs but they still haven't been merged. Please merge them ASAP to keep the branches relatively in sync.

1 similar comment
@kibanamachine
Copy link
Contributor

Looks like this PR has backport PRs but they still haven't been merged. Please merge them ASAP to keep the branches relatively in sync.

CAWilson94 pushed a commit to CAWilson94/kibana that referenced this pull request Mar 22, 2025
…#212478)

## Summary
Part 2 of elastic#212173

### Testing
For setup see testing section here:
elastic#212173 (comment)

**Areas/How to test:**
- For the following pages, test there are no `fields` api requests in
the inspector network tab when visiting from another page. IF YOU
REFRESH on any of these pages, you will see these requests as they are
called by the Query Search Bar and the `useInitSourcerer` call
  - Cases Page
  - Dashboard Page
  - Timelines Page
- Timeline
  - All Tabs
    - Does it show the loading screen on first interaction?
    - Does the `fields` api fire on first interaction with the tab
    - When you navigate back to those tabs, do they not re-render?
- All other pages hosting timeline
 - Do you feel like the performance is generally better?


### Background

When investigating the performance of the security solution application,
one of the issues that was observed was queries to the `fields` api on
pages that had no reason making that request (such as Cases, or the
Dashboards list view). This was due to the background background loaded
tabs of timeline loading the relevant `dataView` necessary for their
search functionality. When the fields request is significantly large
this can have a massive impact on the experience of users on pages that
should be relatively responsive.

To fix this a few changes were made. 

1. First the `withDataView` HOC was removed as it was only used in 2
components that shared a parent - child relationship, and the child
`UnifiedTimeline` was only used in the parent. The hook that HOC calls
was not caching the dataView being created, so `dataView.create` was
being called up to 6 times unnecessarily. Now it is only called once in
each tab.

2. A new wrapper `OnDemandRenderer` (open to different naming 😅) was
created that will not render any of the nested tabs until they are
opened. Once they are opened, they stay in memory, to avoid re-calling
expensive api's every time a user switches tabs.
_Note_: There is currently a known issue where navigating between
various routes in security solution causes the whole application to
unmount and re-mount. Which means every page change will lead to
timeline needing to be re-loaded when the tab is opened. This is being
resolved in a separate effort.

3. Additional checks were added to the `useTimelineEvents` hook to limit
additional re-renders caused by unnecessary reference changes when the
underlying values never actually change

### Checklist

Check the PR satisfies following conditions. 

Reviewers should verify this PR satisfies this list as well.

- [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
### Identify risks
@michaelolo24
Copy link
Contributor Author

💚 All backports created successfully

Status Branch Result
8.x

Note: Successful backport PRs will be merged automatically after passing CI.

Questions ?

Please refer to the Backport tool documentation

michaelolo24 added a commit to michaelolo24/kibana that referenced this pull request Mar 24, 2025
…#212478)

## Summary
Part 2 of elastic#212173

### Testing
For setup see testing section here:
elastic#212173 (comment)

**Areas/How to test:**
- For the following pages, test there are no `fields` api requests in
the inspector network tab when visiting from another page. IF YOU
REFRESH on any of these pages, you will see these requests as they are
called by the Query Search Bar and the `useInitSourcerer` call
  - Cases Page
  - Dashboard Page
  - Timelines Page
- Timeline
  - All Tabs
    - Does it show the loading screen on first interaction?
    - Does the `fields` api fire on first interaction with the tab
    - When you navigate back to those tabs, do they not re-render?
- All other pages hosting timeline
 - Do you feel like the performance is generally better?

### Background

When investigating the performance of the security solution application,
one of the issues that was observed was queries to the `fields` api on
pages that had no reason making that request (such as Cases, or the
Dashboards list view). This was due to the background background loaded
tabs of timeline loading the relevant `dataView` necessary for their
search functionality. When the fields request is significantly large
this can have a massive impact on the experience of users on pages that
should be relatively responsive.

To fix this a few changes were made.

1. First the `withDataView` HOC was removed as it was only used in 2
components that shared a parent - child relationship, and the child
`UnifiedTimeline` was only used in the parent. The hook that HOC calls
was not caching the dataView being created, so `dataView.create` was
being called up to 6 times unnecessarily. Now it is only called once in
each tab.

2. A new wrapper `OnDemandRenderer` (open to different naming 😅) was
created that will not render any of the nested tabs until they are
opened. Once they are opened, they stay in memory, to avoid re-calling
expensive api's every time a user switches tabs.
_Note_: There is currently a known issue where navigating between
various routes in security solution causes the whole application to
unmount and re-mount. Which means every page change will lead to
timeline needing to be re-loaded when the tab is opened. This is being
resolved in a separate effort.

3. Additional checks were added to the `useTimelineEvents` hook to limit
additional re-renders caused by unnecessary reference changes when the
underlying values never actually change

### Checklist

Check the PR satisfies following conditions.

Reviewers should verify this PR satisfies this list as well.

- [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
### Identify risks

(cherry picked from commit 2d8f3c1)
michaelolo24 added a commit that referenced this pull request Mar 24, 2025
…212478) (#215791)

# Backport

This will backport the following commits from `main` to `8.x`:
- [[Performance][Security Solution][2/4] - Timeline Performance
(#212478)](#212478)

<!--- Backport version: 9.6.6 -->

### Questions ?
Please refer to the [Backport tool
documentation](https://github.com/sorenlouv/backport)

<!--BACKPORT [{"author":{"name":"Michael
Olorunnisola","email":"[email protected]"},"sourceCommit":{"committedDate":"2025-03-11T16:56:45Z","message":"[Performance][Security
Solution][2/4] - Timeline Performance (#212478)\n\n## Summary\nPart 2 of
https://github.com/elastic/kibana/pull/212173\n\n### Testing\nFor setup
see testing section
here:\nhttps://github.com//pull/212173#issue-2870522020\n\n**Areas/How
to test:**\n- For the following pages, test there are no `fields` api
requests in\nthe inspector network tab when visiting from another page.
IF YOU\nREFRESH on any of these pages, you will see these requests as
they are\ncalled by the Query Search Bar and the `useInitSourcerer`
call\n - Cases Page\n - Dashboard Page\n - Timelines Page\n- Timeline\n
- All Tabs\n - Does it show the loading screen on first interaction?\n -
Does the `fields` api fire on first interaction with the tab\n - When
you navigate back to those tabs, do they not re-render?\n- All other
pages hosting timeline\n - Do you feel like the performance is generally
better?\n\n\n### Background\n\nWhen investigating the performance of the
security solution application,\none of the issues that was observed was
queries to the `fields` api on\npages that had no reason making that
request (such as Cases, or the\nDashboards list view). This was due to
the background background loaded\ntabs of timeline loading the relevant
`dataView` necessary for their\nsearch functionality. When the fields
request is significantly large\nthis can have a massive impact on the
experience of users on pages that\nshould be relatively
responsive.\n\nTo fix this a few changes were made. \n\n1. First the
`withDataView` HOC was removed as it was only used in 2\ncomponents that
shared a parent - child relationship, and the child\n`UnifiedTimeline`
was only used in the parent. The hook that HOC calls\nwas not caching
the dataView being created, so `dataView.create` was\nbeing called up to
6 times unnecessarily. Now it is only called once in\neach tab.\n\n2. A
new wrapper `OnDemandRenderer` (open to different naming 😅) was\ncreated
that will not render any of the nested tabs until they are\nopened. Once
they are opened, they stay in memory, to avoid re-calling\nexpensive
api's every time a user switches tabs.\n_Note_: There is currently a
known issue where navigating between\nvarious routes in security
solution causes the whole application to\nunmount and re-mount. Which
means every page change will lead to\ntimeline needing to be re-loaded
when the tab is opened. This is being\nresolved in a separate
effort.\n\n3. Additional checks were added to the `useTimelineEvents`
hook to limit\nadditional re-renders caused by unnecessary reference
changes when the\nunderlying values never actually change\n\n###
Checklist\n\nCheck the PR satisfies following conditions. \n\nReviewers
should verify this PR satisfies this list as well.\n\n- [x] [Unit or
functional\ntests](https://www.elastic.co/guide/en/kibana/master/development-tests.html)\nwere
updated or added to match the most common scenarios\n### Identify
risks","sha":"2d8f3c1544aa6bff74623273a278f580df0d918d","branchLabelMapping":{"^v9.1.0$":"main","^v8.19.0$":"8.x","^v(\\d+).(\\d+).\\d+$":"$1.$2"}},"sourcePullRequest":{"labels":["release_note:skip","backport
missing","Team:Threat
Hunting:Investigations","ci:cloud-deploy","ci:project-redeploy","backport:version","v9.1.0","v8.19.0","v8.17.4"],"title":"[Performance][Security
Solution][2/4] - Timeline
Performance","number":212478,"url":"https://github.com/elastic/kibana/pull/212478","mergeCommit":{"message":"[Performance][Security
Solution][2/4] - Timeline Performance (#212478)\n\n## Summary\nPart 2 of
https://github.com/elastic/kibana/pull/212173\n\n### Testing\nFor setup
see testing section
here:\nhttps://github.com//pull/212173#issue-2870522020\n\n**Areas/How
to test:**\n- For the following pages, test there are no `fields` api
requests in\nthe inspector network tab when visiting from another page.
IF YOU\nREFRESH on any of these pages, you will see these requests as
they are\ncalled by the Query Search Bar and the `useInitSourcerer`
call\n - Cases Page\n - Dashboard Page\n - Timelines Page\n- Timeline\n
- All Tabs\n - Does it show the loading screen on first interaction?\n -
Does the `fields` api fire on first interaction with the tab\n - When
you navigate back to those tabs, do they not re-render?\n- All other
pages hosting timeline\n - Do you feel like the performance is generally
better?\n\n\n### Background\n\nWhen investigating the performance of the
security solution application,\none of the issues that was observed was
queries to the `fields` api on\npages that had no reason making that
request (such as Cases, or the\nDashboards list view). This was due to
the background background loaded\ntabs of timeline loading the relevant
`dataView` necessary for their\nsearch functionality. When the fields
request is significantly large\nthis can have a massive impact on the
experience of users on pages that\nshould be relatively
responsive.\n\nTo fix this a few changes were made. \n\n1. First the
`withDataView` HOC was removed as it was only used in 2\ncomponents that
shared a parent - child relationship, and the child\n`UnifiedTimeline`
was only used in the parent. The hook that HOC calls\nwas not caching
the dataView being created, so `dataView.create` was\nbeing called up to
6 times unnecessarily. Now it is only called once in\neach tab.\n\n2. A
new wrapper `OnDemandRenderer` (open to different naming 😅) was\ncreated
that will not render any of the nested tabs until they are\nopened. Once
they are opened, they stay in memory, to avoid re-calling\nexpensive
api's every time a user switches tabs.\n_Note_: There is currently a
known issue where navigating between\nvarious routes in security
solution causes the whole application to\nunmount and re-mount. Which
means every page change will lead to\ntimeline needing to be re-loaded
when the tab is opened. This is being\nresolved in a separate
effort.\n\n3. Additional checks were added to the `useTimelineEvents`
hook to limit\nadditional re-renders caused by unnecessary reference
changes when the\nunderlying values never actually change\n\n###
Checklist\n\nCheck the PR satisfies following conditions. \n\nReviewers
should verify this PR satisfies this list as well.\n\n- [x] [Unit or
functional\ntests](https://www.elastic.co/guide/en/kibana/master/development-tests.html)\nwere
updated or added to match the most common scenarios\n### Identify
risks","sha":"2d8f3c1544aa6bff74623273a278f580df0d918d"}},"sourceBranch":"main","suggestedTargetBranches":[],"targetPullRequestStates":[{"branch":"main","label":"v9.1.0","branchLabelMappingKey":"^v9.1.0$","isSourceBranch":true,"state":"MERGED","url":"https://github.com/elastic/kibana/pull/212478","number":212478,"mergeCommit":{"message":"[Performance][Security
Solution][2/4] - Timeline Performance (#212478)\n\n## Summary\nPart 2 of
https://github.com/elastic/kibana/pull/212173\n\n### Testing\nFor setup
see testing section
here:\nhttps://github.com//pull/212173#issue-2870522020\n\n**Areas/How
to test:**\n- For the following pages, test there are no `fields` api
requests in\nthe inspector network tab when visiting from another page.
IF YOU\nREFRESH on any of these pages, you will see these requests as
they are\ncalled by the Query Search Bar and the `useInitSourcerer`
call\n - Cases Page\n - Dashboard Page\n - Timelines Page\n- Timeline\n
- All Tabs\n - Does it show the loading screen on first interaction?\n -
Does the `fields` api fire on first interaction with the tab\n - When
you navigate back to those tabs, do they not re-render?\n- All other
pages hosting timeline\n - Do you feel like the performance is generally
better?\n\n\n### Background\n\nWhen investigating the performance of the
security solution application,\none of the issues that was observed was
queries to the `fields` api on\npages that had no reason making that
request (such as Cases, or the\nDashboards list view). This was due to
the background background loaded\ntabs of timeline loading the relevant
`dataView` necessary for their\nsearch functionality. When the fields
request is significantly large\nthis can have a massive impact on the
experience of users on pages that\nshould be relatively
responsive.\n\nTo fix this a few changes were made. \n\n1. First the
`withDataView` HOC was removed as it was only used in 2\ncomponents that
shared a parent - child relationship, and the child\n`UnifiedTimeline`
was only used in the parent. The hook that HOC calls\nwas not caching
the dataView being created, so `dataView.create` was\nbeing called up to
6 times unnecessarily. Now it is only called once in\neach tab.\n\n2. A
new wrapper `OnDemandRenderer` (open to different naming 😅) was\ncreated
that will not render any of the nested tabs until they are\nopened. Once
they are opened, they stay in memory, to avoid re-calling\nexpensive
api's every time a user switches tabs.\n_Note_: There is currently a
known issue where navigating between\nvarious routes in security
solution causes the whole application to\nunmount and re-mount. Which
means every page change will lead to\ntimeline needing to be re-loaded
when the tab is opened. This is being\nresolved in a separate
effort.\n\n3. Additional checks were added to the `useTimelineEvents`
hook to limit\nadditional re-renders caused by unnecessary reference
changes when the\nunderlying values never actually change\n\n###
Checklist\n\nCheck the PR satisfies following conditions. \n\nReviewers
should verify this PR satisfies this list as well.\n\n- [x] [Unit or
functional\ntests](https://www.elastic.co/guide/en/kibana/master/development-tests.html)\nwere
updated or added to match the most common scenarios\n### Identify
risks","sha":"2d8f3c1544aa6bff74623273a278f580df0d918d"}},{"branch":"8.x","label":"v8.19.0","branchLabelMappingKey":"^v8.19.0$","isSourceBranch":false,"url":"https://github.com/elastic/kibana/pull/213978","number":213978,"state":"OPEN"},{"branch":"8.17","label":"v8.17.4","branchLabelMappingKey":"^v(\\d+).(\\d+).\\d+$","isSourceBranch":false,"url":"https://github.com/elastic/kibana/pull/213988","number":213988,"state":"MERGED","mergeCommit":{"sha":"3febe25204eaf1c83970a7010ef63ac1d3fa8431","message":"[8.17]
[Performance][Security Solution][2/4] - Timeline Performance (#212478)
(#213988)\n\n# Backport\n\nThis will backport the following commits from
`main` to `8.17`:\n- [[Performance][Security Solution][2/4] - Timeline
Performance\n(#212478)](https://github.com/elastic/kibana/pull/212478)\n\n\n\n###
Questions ?\nPlease refer to the [Backport
tool\ndocumentation](https://github.com/sorenlouv/backport)\n\n"}}]}]
BACKPORT-->
@kibanamachine kibanamachine removed the backport missing Added to PRs automatically when the are determined to be missing a backport. label Mar 24, 2025
@mistic mistic added v8.17.5 and removed v8.17.4 labels Mar 25, 2025
@mistic
Copy link
Member

mistic commented Mar 25, 2025

This PR didn't land on time for the latest 8.17.4 BC. Updating the labels.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
backport:version Backport to applied version labels ci:cloud-deploy Create or update a Cloud deployment ci:project-redeploy Always create a new Cloud project release_note:skip Skip the PR/issue when compiling release notes Team:Threat Hunting:Investigations Security Solution Investigations Team v8.17.5 v8.19.0 v9.1.0
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants