mirror of
https://github.com/gristlabs/grist-core.git
synced 2024-10-27 20:44:07 +00:00
(core) Storing last position for doc and user
Summary: Last position should be stored for document and user. Test Plan: Updated tests Reviewers: georgegevoian Reviewed By: georgegevoian Differential Revision: https://phab.getgrist.com/D3143
This commit is contained in:
parent
c6aa9b65d4
commit
fc50079e03
@ -18,8 +18,8 @@ export class CursorMonitor extends Disposable {
|
||||
|
||||
// abstraction to work with local storage
|
||||
private _store: StorageWrapper;
|
||||
// document id that this monitor is attached
|
||||
private _docId: string;
|
||||
// key for storing position in the memory (docId + userId)
|
||||
private _key: string;
|
||||
// flag that tells if the position was already restored
|
||||
// we track document's view change event, so we only want
|
||||
// to react to that event once
|
||||
@ -31,7 +31,10 @@ export class CursorMonitor extends Disposable {
|
||||
super();
|
||||
|
||||
this._store = new StorageWrapper(store);
|
||||
this._docId = doc.docId();
|
||||
|
||||
// Use document id and user id as a key for storage.
|
||||
const userId = doc.app.topAppModel.appObs.get()?.currentUser?.id ?? null;
|
||||
this._key = doc.docId() + userId;
|
||||
|
||||
/**
|
||||
* When document loads last cursor position should be restored from local storage.
|
||||
@ -77,12 +80,12 @@ export class CursorMonitor extends Disposable {
|
||||
}
|
||||
|
||||
private _storePosition(pos: ViewCursorPos) {
|
||||
this._store.update(this._docId, pos);
|
||||
this._store.update(this._key, pos);
|
||||
}
|
||||
|
||||
private _restoreLastPosition(view: IDocPage) {
|
||||
const lastPosition = this._store.read(this._docId);
|
||||
this._store.clear(this._docId);
|
||||
const lastPosition = this._store.read(this._key);
|
||||
this._store.clear(this._key);
|
||||
if (lastPosition && lastPosition.position.viewId == view) {
|
||||
return lastPosition.position;
|
||||
}
|
||||
|
@ -22,7 +22,10 @@ export class EditorMonitor extends Disposable {
|
||||
super();
|
||||
|
||||
// create store
|
||||
this._store = new EditMemoryStorage(doc.docId(), store);
|
||||
const userId = doc.app.topAppModel.appObs.get()?.currentUser?.id ?? null;
|
||||
// use document id and user id as a key for storage
|
||||
const key = doc.docId() + userId;
|
||||
this._store = new EditMemoryStorage(key, store);
|
||||
|
||||
// listen to document events to handle view load event
|
||||
this._listenToReload(doc);
|
||||
@ -58,8 +61,8 @@ export class EditorMonitor extends Disposable {
|
||||
// will be invoked only once
|
||||
let executed = false;
|
||||
|
||||
// don't restore on readonly mode
|
||||
if (doc.isReadonly.get()) { return; }
|
||||
// don't restore on readonly mode or when there is custom nav
|
||||
if (doc.isReadonly.get() || doc.hasCustomNav.get()) { return; }
|
||||
|
||||
// on view shown
|
||||
this._currentViewListener.autoDispose(doc.currentView.addListener(async view => {
|
||||
@ -114,7 +117,7 @@ class EditMemoryStorage {
|
||||
private _entry: LastEditData | null = null;
|
||||
private _timestamp = 0;
|
||||
|
||||
constructor(private _docId: string, private _storage = getStorage()) {
|
||||
constructor(private _key: string, private _storage = getStorage()) {
|
||||
}
|
||||
|
||||
public updateValue(pos: CellPosition, value: EditorState): void {
|
||||
@ -136,13 +139,13 @@ class EditMemoryStorage {
|
||||
return this._timestamp;
|
||||
}
|
||||
|
||||
protected _key() {
|
||||
return `grist-last-edit-${this._docId}`;
|
||||
protected _storageKey() {
|
||||
return `grist-last-edit-${this._key}`;
|
||||
}
|
||||
|
||||
protected load() {
|
||||
const storage = this._storage;
|
||||
const data = storage.getItem(this._key());
|
||||
const data = storage.getItem(this._storageKey());
|
||||
this._entry = null;
|
||||
this._timestamp = 0;
|
||||
|
||||
@ -166,14 +169,14 @@ class EditMemoryStorage {
|
||||
|
||||
// if entry was removed - clear the storage
|
||||
if (!this._entry) {
|
||||
storage.removeItem(this._key());
|
||||
storage.removeItem(this._storageKey());
|
||||
return;
|
||||
}
|
||||
|
||||
try {
|
||||
this._timestamp = Date.now();
|
||||
const data = { timestamp: this._timestamp, entry: this._entry };
|
||||
storage.setItem(this._key(), JSON.stringify(data));
|
||||
storage.setItem(this._storageKey(), JSON.stringify(data));
|
||||
} catch (ex) {
|
||||
console.error("Can't save current edited cell state. Error message: " + ex?.message);
|
||||
}
|
||||
|
@ -1838,6 +1838,20 @@ export async function getEnabledOptions(): Promise<SortOption[]> {
|
||||
return options;
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs action in a separate tab, closing the tab after.
|
||||
* In case of an error tab is not closed, consider using cleanupExtraWindows
|
||||
* on whole test suit if needed.
|
||||
*/
|
||||
export async function onNewTab(action: () => Promise<void>) {
|
||||
await driver.executeScript("return window.open('about:blank', '_blank')");
|
||||
const tabs = await driver.getAllWindowHandles();
|
||||
await driver.switchTo().window(tabs[tabs.length - 1]);
|
||||
await action();
|
||||
await driver.close();
|
||||
await driver.switchTo().window(tabs[tabs.length - 2]);
|
||||
}
|
||||
|
||||
} // end of namespace gristUtils
|
||||
|
||||
stackWrapOwnMethods(gristUtils);
|
||||
|
Loading…
Reference in New Issue
Block a user