-
Notifications
You must be signed in to change notification settings - Fork 8.3k
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
[data views] cache field caps requests #168910
[data views] cache field caps requests #168910
Conversation
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.
Thanks for looking into this, and it definitely feels like a step in the right direction. In my local testing, it seems to work reliably in some situations and less so in others. For example, Data View Management seems to fairly reliably cache the requests across page navigations and page reloads, but the same requests in Discover weren't being cached reliably. Even without a page reload, it seemed like the cache wasn't being used reliably for duplicate GET _fields_for_wildcard
requests.
HTTP caching is pretty hard to understand and troubleshoot, but after looking into it I suspect this is at least partly related to cache validation requests on page reload. It's possible we can improve this using ETag
and/or Last-Modified
headers, but I'm not entirely sure.
Some possibly related SO questions I encountered while looking into this (adding here for future reference):
- https://stackoverflow.com/questions/76769130/why-does-google-chrome-not-honor-the-caching-headers
- https://stackoverflow.com/questions/35218458/chromes-cache-not-working-when-refreshing
- https://stackoverflow.com/questions/63162653/why-isnt-chrome-caching-responses-even-when-cache-control-header-is-present
- https://stackoverflow.com/questions/16873263/load-from-cache-with-window-location-reload-and-hash-fragment-in-chrome-doesnt
- https://stackoverflow.com/questions/45829055/why-doesnt-chrome-re-validate-in-memory-cache-when-doing-a-normal-reload
- https://stackoverflow.com/questions/49246803/why-browser-doesnt-get-content-from-cache-during-recursive-refresh-after-first
All of this makes me wonder if maybe we should be taking more control over the caching than what HTTP headers provide us. Even if we figure out the reload issue, the Cache-Control
headers are still only a hint to the browser about what it's allowed to do, which it may choose to ignore anyway. I think exploring HTTP headers was a good idea and may still be the right approach in the end (and I think the stale-while-revalidate strategy is the way to go regardless of how we implement it), but for completeness I think it's also worth us exploring a custom stale-while-revalidate strategy that interacts directly with the browser cache through the cache API:
src/plugins/data_views/public/data_views/data_views_api_client.ts
Outdated
Show resolved
Hide resolved
src/plugins/data_views/public/data_views/data_views_api_client.ts
Outdated
Show resolved
Hide resolved
src/plugins/data_views/server/rest_api_routes/internal/fields_for.ts
Outdated
Show resolved
Hide resolved
Pinging @elastic/kibana-data-discovery (Team:DataDiscovery) |
…om:mattkime/kibana into fields_for_wildcard_stale_while_revalidate
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 for Core changes, just one remark
packages/core/http/core-http-router-server-internal/src/response.ts
Outdated
Show resolved
Hide resolved
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!
…om:mattkime/kibana into fields_for_wildcard_stale_while_revalidate
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.
Tested locally one last time, and the remaining two issues I reported have been resolved -- thanks for updating the tests too 👍 Great work on this, and I think it's time to get this merged in. Thanks for all the work on it, and LGTM!
|
||
expect(fetchSpy).toHaveBeenCalledWith(expectedPath, expect.any(Object)); | ||
expect(fetchSpy).toHaveBeenCalledWith(expectedPath, { | ||
// not sure what asResponse is but the rest of the results are useful |
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 asResponse
just prevents the HTTP service from automatically parsing the response as JSON so we can deal with it in its raw form (which makes sense since we're doing ETags, etc.).
@@ -104,7 +104,8 @@ export class DataViewsApiClient implements IDataViewsApiClient { | |||
allow_no_index: allowNoIndex, | |||
include_unmapped: includeUnmapped, | |||
fields, | |||
allow_hidden: allowHidden, | |||
// default to undefined to keep value out of URL params and improve caching | |||
allow_hidden: allowHidden || undefined, |
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 approach is much nicer than addressing each caller separately 👍 no need to try to remember it in future changes.
💛 Build succeeded, but was flaky
Failed CI StepsTest FailuresMetrics [docs]Public APIs missing comments
Any counts in public APIs
Async chunks
Page load bundle
Unknown metric groupsAPI count
ESLint disabled line counts
Total ESLint disabled count
History
To update your PR or re-run it, just comment with: cc @mattkime |
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.
logs-shared
changes LGTM!
## Summary tldr; The implements a fallback sha1 method when using the browser in an insecure context. The data views fields requests cache need uniqueness across users. This has been implemented by hashing the user object into a HTTP header using sha1. Typically we can use the browser's built in crypto objects for this HOWEVER its not available in insecure contexts - https://www.chromium.org/blink/webcrypto/#accessing-it - this PR supplies a sha1 function for insecure contexts. How to test - when running kibana locally, it will run in a secure context via 127.0.0.1 or localhost. It will run in an insecure context at 0.0.0.0. Simply load some sample data and load a data view. follow up to #168910 Screenshot of error resolved by this pr - ![Visualize Visualize Reporting Screenshots Print PDF button becomes available whe-c57ca69f29465527c4079569a4548eb10fe0568302776500148260b299fbd5c4](https://github.com/elastic/kibana/assets/216176/d7bcec41-631f-426f-b209-87b2d6403f23) --------- Co-authored-by: kibanamachine <[email protected]>
…#175181) ## Summary tldr; The implements a fallback sha1 method when using the browser in an insecure context. The data views fields requests cache need uniqueness across users. This has been implemented by hashing the user object into a HTTP header using sha1. Typically we can use the browser's built in crypto objects for this HOWEVER its not available in insecure contexts - https://www.chromium.org/blink/webcrypto/#accessing-it - this PR supplies a sha1 function for insecure contexts. How to test - when running kibana locally, it will run in a secure context via 127.0.0.1 or localhost. It will run in an insecure context at 0.0.0.0. Simply load some sample data and load a data view. follow up to elastic#168910 Screenshot of error resolved by this pr - ![Visualize Visualize Reporting Screenshots Print PDF button becomes available whe-c57ca69f29465527c4079569a4548eb10fe0568302776500148260b299fbd5c4](https://github.com/elastic/kibana/assets/216176/d7bcec41-631f-426f-b209-87b2d6403f23) --------- Co-authored-by: kibanamachine <[email protected]>
Summary
Closes: #169622
Field caps request caching - implement
stale-while-revalidate
cache headers and etags with 304 responses as appropriate.This PR accomplishes
/internal/data_views/fields
endpoint which supports caching.fields_for_wildcard
doesn't support caching due to POST requestsstale-while-revalidate
header directive UNLESS field list is empty.How to test
data_views:cache_max_age
, shift reload. No field requests will be cached.Note on Safari
Safari doesn't support the
stale-while-revalidate
directive. Additionally, the Safari dev console shows 304 responses as 200's. I figured this out by adding console statements to the fields endpoint. As best I can tell, Safari won't be performant on slow clusters but its also no slower than it was before this PR. Safari does respect the disabling of cache headers.Release note
Data View field list requests are now cached with a
stale-while-revalidate
strategy. This means that after the initial field list request, all subsequent requests return the cached response which is very fast. If the cache is determined to be stale then the cache will update in the background and new data will be available on the next request.This behavior can be modified via the
data_views:cache_max_age
Kibana advanced setting. Setting it to zero will disable the cache. All other values (in seconds) will be used to determine whether the cache is stale. The default value is 5 seconds.The field list can be manually updated via the refresh button in data view management or a hard refresh with your browser.
Note for Safari: The
stale-while-revalidate
cache directive is unsupported, therefore it makes additional requests. If this is impacting Kibana performance then try Chrome or Firefox.Data View Management