Try switching some files over to TypeScript

This commit is contained in:
Danila Fedorin 2021-08-05 17:03:46 -07:00
parent d5503b2e6b
commit a7adc27a69
4 changed files with 59 additions and 33 deletions

View file

@ -18,20 +18,26 @@ limitations under the License.
import {EventKey} from "../EventKey.js"; import {EventKey} from "../EventKey.js";
export const PENDING_FRAGMENT_ID = Number.MAX_SAFE_INTEGER; export const PENDING_FRAGMENT_ID = Number.MAX_SAFE_INTEGER;
export class BaseEntry { export interface FragmentIdComparer {
compare(a: number, b: number): number;
}
export abstract class BaseEntry {
protected _fragmentIdComparer: FragmentIdComparer
constructor(fragmentIdComparer) { constructor(fragmentIdComparer) {
this._fragmentIdComparer = fragmentIdComparer; this._fragmentIdComparer = fragmentIdComparer;
} }
get fragmentId() { get fragmentId(): number {
throw new Error("unimplemented"); throw new Error("unimplemented");
} }
get entryIndex() { get entryIndex(): number {
throw new Error("unimplemented"); throw new Error("unimplemented");
} }
compare(otherEntry) { compare(otherEntry: BaseEntry): number {
if (this.fragmentId === otherEntry.fragmentId) { if (this.fragmentId === otherEntry.fragmentId) {
return this.entryIndex - otherEntry.entryIndex; return this.entryIndex - otherEntry.entryIndex;
} else if (this.fragmentId === PENDING_FRAGMENT_ID) { } else if (this.fragmentId === PENDING_FRAGMENT_ID) {
@ -44,9 +50,9 @@ export class BaseEntry {
} }
} }
asEventKey() { asEventKey(): EventKey {
return new EventKey(this.fragmentId, this.entryIndex); return new EventKey(this.fragmentId, this.entryIndex);
} }
updateFrom() {} updateFrom(other: BaseEntry) {}
} }

View file

@ -14,33 +14,48 @@ See the License for the specific language governing permissions and
limitations under the License. limitations under the License.
*/ */
import {BaseEntry} from "./BaseEntry.js"; import {FragmentIdComparer, BaseEntry} from "./BaseEntry";
import {PendingEventEntry} from "./PendingEventEntry.js"
import {REDACTION_TYPE} from "../../common.js"; import {REDACTION_TYPE} from "../../common.js";
import {createAnnotation, ANNOTATION_RELATION_TYPE, getRelationFromContent} from "../relations.js"; import {createAnnotation, ANNOTATION_RELATION_TYPE, getRelationFromContent} from "../relations.js";
import {PendingAnnotation} from "../PendingAnnotation.js"; import {PendingAnnotation} from "../PendingAnnotation.js";
export interface Annotation {
count: number,
me: boolean,
firstTimestamp: number
}
/** Deals mainly with local echo for relations and redactions, /** Deals mainly with local echo for relations and redactions,
* so it is shared between PendingEventEntry and EventEntry */ * so it is shared between PendingEventEntry and EventEntry */
export class BaseEventEntry extends BaseEntry { export abstract class BaseEventEntry extends BaseEntry {
constructor(fragmentIdComparer) { private _pendingRedactions: Array<PendingEventEntry> | null
private _pendingAnnotations: Map<string, PendingAnnotation> | null
abstract id: string
abstract relatedEventId: string
abstract eventType: string
abstract content: any
constructor(fragmentIdComparer: FragmentIdComparer) {
super(fragmentIdComparer); super(fragmentIdComparer);
this._pendingRedactions = null; this._pendingRedactions = null;
this._pendingAnnotations = null; this._pendingAnnotations = null;
} }
get isRedacting() { get isRedacting(): boolean {
return !!this._pendingRedactions; return !!this._pendingRedactions;
} }
get isRedacted() { get isRedacted(): boolean {
return this.isRedacting; return this.isRedacting;
} }
get isRedaction() { get isRedaction(): boolean {
return this.eventType === REDACTION_TYPE; return this.eventType === REDACTION_TYPE;
} }
get redactionReason() { get redactionReason(): string | null {
if (this._pendingRedactions) { if (this._pendingRedactions) {
return this._pendingRedactions[0].content?.reason; return this._pendingRedactions[0].content?.reason;
} }
@ -51,7 +66,7 @@ export class BaseEventEntry extends BaseEntry {
aggregates local relation or local redaction of remote relation. aggregates local relation or local redaction of remote relation.
@return [string] returns the name of the field that has changed, if any @return [string] returns the name of the field that has changed, if any
*/ */
addLocalRelation(entry) { addLocalRelation(entry: PendingEventEntry): string | undefined {
if (entry.eventType === REDACTION_TYPE && entry.isRelatedToId(this.id)) { if (entry.eventType === REDACTION_TYPE && entry.isRelatedToId(this.id)) {
if (!this._pendingRedactions) { if (!this._pendingRedactions) {
this._pendingRedactions = []; this._pendingRedactions = [];
@ -76,7 +91,7 @@ export class BaseEventEntry extends BaseEntry {
deaggregates local relation or a local redaction of a remote relation. deaggregates local relation or a local redaction of a remote relation.
@return [string] returns the name of the field that has changed, if any @return [string] returns the name of the field that has changed, if any
*/ */
removeLocalRelation(entry) { removeLocalRelation(entry: PendingEventEntry): string | undefined {
if (entry.eventType === REDACTION_TYPE && entry.isRelatedToId(this.id) && this._pendingRedactions) { if (entry.eventType === REDACTION_TYPE && entry.isRelatedToId(this.id) && this._pendingRedactions) {
const countBefore = this._pendingRedactions.length; const countBefore = this._pendingRedactions.length;
this._pendingRedactions = this._pendingRedactions.filter(e => e !== entry); this._pendingRedactions = this._pendingRedactions.filter(e => e !== entry);
@ -98,7 +113,7 @@ export class BaseEventEntry extends BaseEntry {
} }
} }
_addPendingAnnotation(entry) { _addPendingAnnotation(entry: PendingEventEntry): boolean {
if (!this._pendingAnnotations) { if (!this._pendingAnnotations) {
this._pendingAnnotations = new Map(); this._pendingAnnotations = new Map();
} }
@ -115,14 +130,14 @@ export class BaseEventEntry extends BaseEntry {
return false; return false;
} }
_removePendingAnnotation(entry) { _removePendingAnnotation(entry: PendingEventEntry) {
const {key} = (entry.redactingEntry || entry).relation; const {key} = (entry.redactingEntry || entry).relation;
if (key) { if (key) {
let annotation = this._pendingAnnotations.get(key); let annotation = this._pendingAnnotations?.get(key);
if (annotation.remove(entry) && annotation.isEmpty) { if (annotation.remove(entry) && annotation.isEmpty) {
this._pendingAnnotations.delete(key); this._pendingAnnotations?.delete(key);
} }
if (this._pendingAnnotations.size === 0) { if (this._pendingAnnotations?.size === 0) {
this._pendingAnnotations = null; this._pendingAnnotations = null;
} }
return true; return true;
@ -140,23 +155,23 @@ export class BaseEventEntry extends BaseEntry {
} }
} }
get pendingRedaction() { get pendingRedaction(): PendingEventEntry | null {
if (this._pendingRedactions) { if (this._pendingRedactions) {
return this._pendingRedactions[0]; return this._pendingRedactions[0];
} }
return null; return null;
} }
annotate(key) { annotate(key: string): any {
return createAnnotation(this.id, key); return createAnnotation(this.id, key);
} }
/** takes both remote event id and local txn id into account, see overriding in PendingEventEntry */ /** takes both remote event id and local txn id into account, see overriding in PendingEventEntry */
isRelatedToId(id) { isRelatedToId(id: string | null): boolean {
return id && this.relatedEventId === id; return !!id && this.relatedEventId === id;
} }
haveAnnotation(key) { haveAnnotation(key: string): boolean {
const haveRemoteReaction = this.annotations?.[key]?.me || false; const haveRemoteReaction = this.annotations?.[key]?.me || false;
const pendingAnnotation = this.pendingAnnotations?.get(key); const pendingAnnotation = this.pendingAnnotations?.get(key);
const willAnnotate = pendingAnnotation?.willAnnotate || false; const willAnnotate = pendingAnnotation?.willAnnotate || false;
@ -170,15 +185,15 @@ export class BaseEventEntry extends BaseEntry {
(!haveRemoteReaction && willAnnotate); (!haveRemoteReaction && willAnnotate);
} }
get relation() { get relation(): any {
return getRelationFromContent(this.content); return getRelationFromContent(this.content);
} }
get pendingAnnotations() { get pendingAnnotations(): Map<string, PendingAnnotation> | null {
return this._pendingAnnotations; return this._pendingAnnotations;
} }
get annotations() { get annotations(): { [key: string]: Annotation } | null {
return null; //overwritten in EventEntry return null; //overwritten in EventEntry
} }
} }

View file

@ -14,25 +14,30 @@ See the License for the specific language governing permissions and
limitations under the License. limitations under the License.
*/ */
import {FragmentIdComparer} from "./BaseEntry.js"
import {BaseEventEntry} from "./BaseEventEntry.js"; import {BaseEventEntry} from "./BaseEventEntry.js";
import {getPrevContentFromStateEvent, isRedacted} from "../../common.js"; import {getPrevContentFromStateEvent, isRedacted} from "../../common.js";
import {getRelatedEventId} from "../relations.js"; import {getRelatedEventId} from "../relations.js";
export class EventEntry extends BaseEventEntry { export class EventEntry extends BaseEventEntry {
constructor(eventEntry, fragmentIdComparer) { private _eventEntry: any // TODO Need type
private _decryptionError: Error | null
private _decryptionResult: any | null // TODO Need type
constructor(eventEntry: any, fragmentIdComparer: FragmentIdComparer = { compare: (x, y) => 0 }) {
super(fragmentIdComparer); super(fragmentIdComparer);
this._eventEntry = eventEntry; this._eventEntry = eventEntry;
this._decryptionError = null; this._decryptionError = null;
this._decryptionResult = null; this._decryptionResult = null;
} }
clone() { clone(): EventEntry {
const clone = new EventEntry(this._eventEntry, this._fragmentIdComparer); const clone = new EventEntry(this._eventEntry, this._fragmentIdComparer);
clone.updateFrom(this); clone.updateFrom(this);
return clone; return clone;
} }
updateFrom(other) { updateFrom(other: EventEntry) {
super.updateFrom(other); super.updateFrom(other);
if (other._decryptionResult && !this._decryptionResult) { if (other._decryptionResult && !this._decryptionResult) {
this._decryptionResult = other._decryptionResult; this._decryptionResult = other._decryptionResult;

View file

@ -14,8 +14,8 @@ See the License for the specific language governing permissions and
limitations under the License. limitations under the License.
*/ */
import {PENDING_FRAGMENT_ID} from "./BaseEntry.js"; import {PENDING_FRAGMENT_ID} from "./BaseEntry";
import {BaseEventEntry} from "./BaseEventEntry.js"; import {BaseEventEntry} from "./BaseEventEntry";
export class PendingEventEntry extends BaseEventEntry { export class PendingEventEntry extends BaseEventEntry {
constructor({pendingEvent, member, clock, redactingEntry}) { constructor({pendingEvent, member, clock, redactingEntry}) {