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

Only emit 'update' events after the entire state cache has been updated. #433

Merged
merged 1 commit into from
Mar 20, 2022
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
42 changes: 32 additions & 10 deletions src/client.ts
Original file line number Diff line number Diff line change
Expand Up @@ -155,20 +155,28 @@ export default class Client {
*/
cacheState(state: State) {

this.cache.store(state);
for(const invByLink of state.links.getMany('inv-by')) {
this.addCacheDependency(resolve(invByLink), state.uri);
// Flatten the list of state objects.
const newStates = flattenState(state);

// Register all cache dependencies.
for(const nState of newStates) {
for(const invByLink of nState.links.getMany('inv-by')) {
this.addCacheDependency(resolve(invByLink), state.uri);
}
}

const resource = this.resources.get(state.uri);
if (resource) {
// We have a resource for this object, notify it as well.
resource.emit('update', state);
// Store all new caches
for(const nState of newStates) {
this.cache.store(nState);
}

for(const embeddedState of state.getEmbedded()) {
// Recursion. MADNESS
this.cacheState(embeddedState);
// Emit 'update' events
for(const nState of newStates) {
const resource = this.resources.get(nState.uri);
if (resource) {
// We have a resource for this object, notify it as well.
resource.emit('update', nState);
}
}

}
Expand Down Expand Up @@ -307,3 +315,17 @@ function expandCacheDependencies(uris: Set<string>, dependencies: Map<string, Se
return output;

}

/**
* Take a State object, find all it's embedded resources and return a flat
* array of all resources at any depth.
*/
function flattenState(state: State, result: Set<State> = new Set<State>()): Set<State> {

result.add(state);
for(const embedded of state.getEmbedded()) {
flattenState(embedded, result);
}
return result;

}