1
0

improve in-memory change handling

The base view now does a better job at keeping the sessions list up to
date with the current session, without having to reload it all the time.

The purpose of this is to be able to show the list and the current
session at the same time, and keep them in sync without polling the
database.
This commit is contained in:
Adrian Wannenmacher 2026-03-01 03:14:00 +01:00
parent de0fc8c917
commit 8a1140688e
Signed by: tfld
GPG Key ID: 19D986ECB1E492D5

View File

@ -39,9 +39,18 @@ class BaseViewModel {
return this.#current;
}
#setCurrent(value) {
if (this.#current !== null)
this.#current.removeEventListener(
Session.EVENT_CHANGE, this.#handleCurrentUpdate);
if (value !== null)
value.addEventListener(Session.EVENT_CHANGE, this.#handleCurrentUpdate);
this.#current = value;
}
set current(value) {
if (value instanceof Session) {
this.#current = value;
this.#setCurrent(value);
this.#currentLoading = null;
} else if (typeof value === "number") {
@ -52,7 +61,7 @@ class BaseViewModel {
.get(value)
.then((s) => {
if (this.#currentLoading === s?.id)
this.#current = s;
this.#setCurrent(s);
})
.catch((e) => {
console.error("failed to load session: ", e);
@ -66,9 +75,8 @@ class BaseViewModel {
} else if (value === null) {
if (this.#current === null)
return;
this.#current = null;
this.#setCurrent(null);
this.#currentLoading = null;
this.loadAllSessions();
} else {
throw new TypeError("current session must be session or id or null");
@ -92,7 +100,8 @@ class BaseViewModel {
.put(session)
.then(() => {
if (this.#currentLoading === BaseViewModel.#newSessionMarker) {
this.#current = session;
this.#setCurrent(session);
this.#sessions.splice(0, 0, session);
m.route.set("/", { session: session.id }, { replace: true });
}
})
@ -132,4 +141,22 @@ class BaseViewModel {
m.redraw();
});
}
#handleCurrentUpdate = (e) => {
if (this.#current !== e.target || this.#current === this.#sessions[0]) {
e.target.removeEventListener(
Session.EVENT_CHANGE, this.#handleCurrentUpdate);
return;
}
if (this.#current?.id === this.#sessions[0]?.id) {
e.target.removeEventListener(
Session.EVENT_CHANGE, this.#handleCurrentUpdate);
this.#sessions[0] = this.#current;
return;
}
this.loadAllSessions();
};
}