-
Notifications
You must be signed in to change notification settings - Fork 877
fix: dedupe concurrent getNodeAjaxOptions requests (#10155) #10159
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
base: master
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -77,6 +77,13 @@ export function generateNodeUrl(treeNodeInfo, actionType, itemNodeData, withId, | |||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
| /* Tracks AJAX requests that are currently in flight, keyed by the resolved | ||||||||||||||||||||||||||||||||||||||||||
| * URL + query params. This lets concurrent callers asking for the same options | ||||||||||||||||||||||||||||||||||||||||||
| * (e.g. every row's Data Type dropdown mounting at once) share a single HTTP | ||||||||||||||||||||||||||||||||||||||||||
| * request instead of each firing their own before the cache is populated. | ||||||||||||||||||||||||||||||||||||||||||
| */ | ||||||||||||||||||||||||||||||||||||||||||
| const _inflightAjaxRequests = new Map(); | ||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
| /* Get the nodes list as options required by select controls | ||||||||||||||||||||||||||||||||||||||||||
| * The options are cached for performance reasons. | ||||||||||||||||||||||||||||||||||||||||||
| */ | ||||||||||||||||||||||||||||||||||||||||||
|
|
@@ -114,15 +121,28 @@ export function getNodeAjaxOptions(url, nodeObj, treeNodeInfo, itemNodeData, par | |||||||||||||||||||||||||||||||||||||||||
| let data = cacheNode.cache(nodeObj.type + '#' + url, treeNodeInfo, cacheLevel); | ||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
| if (_.isUndefined(data) || _.isNull(data)) { | ||||||||||||||||||||||||||||||||||||||||||
| api.get(fullUrl, { | ||||||||||||||||||||||||||||||||||||||||||
| params: otherParams.urlParams, | ||||||||||||||||||||||||||||||||||||||||||
| }).then((res)=>{ | ||||||||||||||||||||||||||||||||||||||||||
| data = res.data; | ||||||||||||||||||||||||||||||||||||||||||
| if(res.data.data) { | ||||||||||||||||||||||||||||||||||||||||||
| data = res.data.data; | ||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||
| otherParams.useCache && cacheNode.cache(nodeObj.type + '#' + url, treeNodeInfo, cacheLevel, data); | ||||||||||||||||||||||||||||||||||||||||||
| resolve(transform(data)); | ||||||||||||||||||||||||||||||||||||||||||
| // Share a single in-flight request among all concurrent callers asking | ||||||||||||||||||||||||||||||||||||||||||
| // for the same URL + params, so we don't fire duplicate GETs before the | ||||||||||||||||||||||||||||||||||||||||||
| // first response lands and populates the cache. | ||||||||||||||||||||||||||||||||||||||||||
| let inflightKey = fullUrl + '#' + JSON.stringify(otherParams.urlParams || {}); | ||||||||||||||||||||||||||||||||||||||||||
| let request = _inflightAjaxRequests.get(inflightKey); | ||||||||||||||||||||||||||||||||||||||||||
| if (!request) { | ||||||||||||||||||||||||||||||||||||||||||
| request = api.get(fullUrl, { | ||||||||||||||||||||||||||||||||||||||||||
| params: otherParams.urlParams, | ||||||||||||||||||||||||||||||||||||||||||
| }).then((res)=>{ | ||||||||||||||||||||||||||||||||||||||||||
| let resData = res.data; | ||||||||||||||||||||||||||||||||||||||||||
| if(res.data.data) { | ||||||||||||||||||||||||||||||||||||||||||
| resData = res.data.data; | ||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||
| otherParams.useCache && cacheNode.cache(nodeObj.type + '#' + url, treeNodeInfo, cacheLevel, resData); | ||||||||||||||||||||||||||||||||||||||||||
| return resData; | ||||||||||||||||||||||||||||||||||||||||||
| }).finally(()=>{ | ||||||||||||||||||||||||||||||||||||||||||
| _inflightAjaxRequests.delete(inflightKey); | ||||||||||||||||||||||||||||||||||||||||||
| }); | ||||||||||||||||||||||||||||||||||||||||||
| _inflightAjaxRequests.set(inflightKey, request); | ||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||
| request.then((resData)=>{ | ||||||||||||||||||||||||||||||||||||||||||
| resolve(transform(resData)); | ||||||||||||||||||||||||||||||||||||||||||
|
Comment on lines
+137
to
+145
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🎯 Functional Correctness | 🟠 Major | ⚡ Quick win Move cache population outside the shared promise to avoid closure capture of the first caller's arguments. The shared Moving the 🐛 Proposed fix- otherParams.useCache && cacheNode.cache(nodeObj.type + '#' + url, treeNodeInfo, cacheLevel, resData);
return resData;
}).finally(()=>{
_inflightAjaxRequests.delete(inflightKey);
});
_inflightAjaxRequests.set(inflightKey, request);
}
request.then((resData)=>{
+ if (otherParams.useCache) {
+ cacheNode.cache(nodeObj.type + '#' + url, treeNodeInfo, cacheLevel, resData);
+ }
resolve(transform(resData));📝 Committable suggestion
Suggested change
🤖 Prompt for AI Agents |
||||||||||||||||||||||||||||||||||||||||||
| }).catch((err)=>{ | ||||||||||||||||||||||||||||||||||||||||||
| reject(err instanceof Error ? err : Error('Something went wrong')); | ||||||||||||||||||||||||||||||||||||||||||
| }); | ||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
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.
Some observations -
vs
And a nested object will make it worse.