-
Notifications
You must be signed in to change notification settings - Fork 7
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Fix onUpdate when PK is of type Identity
When the primary key is of type Identity we were still doing === comparison by using the Map data structure. This commit introduces a different data structure called OperationsMap which can also use isEqual to compare keys if isEqual function is available
- Loading branch information
Showing
4 changed files
with
315 additions
and
3 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,45 @@ | ||
export default class OperationsMap<K, V> { | ||
private items: { key: K; value: V }[] = []; | ||
|
||
private isEqual(a: K, b: K): boolean { | ||
if (a && typeof a === "object" && "isEqual" in a) { | ||
return (a as any).isEqual(b); | ||
} | ||
return a === b; | ||
} | ||
|
||
set(key: K, value: V): void { | ||
const existingIndex = this.items.findIndex(({ key: k }) => | ||
this.isEqual(k, key) | ||
); | ||
if (existingIndex > -1) { | ||
this.items[existingIndex].value = value; | ||
} else { | ||
this.items.push({ key, value }); | ||
} | ||
} | ||
|
||
get(key: K): V | undefined { | ||
const item = this.items.find(({ key: k }) => this.isEqual(k, key)); | ||
return item ? item.value : undefined; | ||
} | ||
|
||
delete(key: K): boolean { | ||
const existingIndex = this.items.findIndex(({ key: k }) => | ||
this.isEqual(k, key) | ||
); | ||
if (existingIndex > -1) { | ||
this.items.splice(existingIndex, 1); | ||
return true; | ||
} | ||
return false; | ||
} | ||
|
||
has(key: K): boolean { | ||
return this.items.some(({ key: k }) => this.isEqual(k, key)); | ||
} | ||
|
||
values(): Array<V> { | ||
return this.items.map((i) => i.value); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,145 @@ | ||
// THIS FILE IS AUTOMATICALLY GENERATED BY SPACETIMEDB. EDITS TO THIS FILE | ||
// WILL NOT BE SAVED. MODIFY TABLES IN RUST INSTEAD. | ||
|
||
// @ts-ignore | ||
import { | ||
__SPACETIMEDB__, | ||
AlgebraicType, | ||
ProductType, | ||
BuiltinType, | ||
ProductTypeElement, | ||
SumType, | ||
SumTypeVariant, | ||
IDatabaseTable, | ||
AlgebraicValue, | ||
ReducerEvent, | ||
Identity, | ||
} from "../../src/index"; | ||
|
||
export class User extends IDatabaseTable { | ||
public static tableName = "User"; | ||
public identity: Identity; | ||
public username: string; | ||
|
||
public static primaryKey: string | undefined = "identity"; | ||
|
||
constructor(identity: Identity, username: string) { | ||
super(); | ||
this.identity = identity; | ||
this.username = username; | ||
} | ||
|
||
public static serialize(value: User): object { | ||
return [Array.from(value.identity.toUint8Array()), value.username]; | ||
} | ||
|
||
public static getAlgebraicType(): AlgebraicType { | ||
return AlgebraicType.createProductType([ | ||
new ProductTypeElement( | ||
"identity", | ||
AlgebraicType.createProductType([ | ||
new ProductTypeElement( | ||
"__identity_bytes", | ||
AlgebraicType.createArrayType( | ||
AlgebraicType.createPrimitiveType(BuiltinType.Type.U8) | ||
) | ||
), | ||
]) | ||
), | ||
new ProductTypeElement( | ||
"username", | ||
AlgebraicType.createPrimitiveType(BuiltinType.Type.String) | ||
), | ||
]); | ||
} | ||
|
||
public static fromValue(value: AlgebraicValue): User { | ||
let productValue = value.asProductValue(); | ||
let __identity = new Identity( | ||
productValue.elements[0].asProductValue().elements[0].asBytes() | ||
); | ||
let __username = productValue.elements[1].asString(); | ||
return new this(__identity, __username); | ||
} | ||
|
||
public static count(): number { | ||
return __SPACETIMEDB__.clientDB.getTable("User").count(); | ||
} | ||
|
||
public static all(): User[] { | ||
return __SPACETIMEDB__.clientDB | ||
.getTable("User") | ||
.getInstances() as unknown as User[]; | ||
} | ||
|
||
public static filterByIdentity(value: Identity): User | null { | ||
for (let instance of __SPACETIMEDB__.clientDB | ||
.getTable("User") | ||
.getInstances()) { | ||
if (instance.identity.isEqual(value)) { | ||
return instance; | ||
} | ||
} | ||
return null; | ||
} | ||
|
||
public static filterByUsername(value: string): User[] { | ||
let result: User[] = []; | ||
for (let instance of __SPACETIMEDB__.clientDB | ||
.getTable("User") | ||
.getInstances()) { | ||
if (instance.username === value) { | ||
result.push(instance); | ||
} | ||
} | ||
return result; | ||
} | ||
|
||
public static onInsert( | ||
callback: (value: User, reducerEvent: ReducerEvent | undefined) => void | ||
) { | ||
__SPACETIMEDB__.clientDB.getTable("User").onInsert(callback); | ||
} | ||
|
||
public static onUpdate( | ||
callback: ( | ||
oldValue: User, | ||
newValue: User, | ||
reducerEvent: ReducerEvent | undefined | ||
) => void | ||
) { | ||
__SPACETIMEDB__.clientDB.getTable("User").onUpdate(callback); | ||
} | ||
|
||
public static onDelete( | ||
callback: (value: User, reducerEvent: ReducerEvent | undefined) => void | ||
) { | ||
__SPACETIMEDB__.clientDB.getTable("User").onDelete(callback); | ||
} | ||
|
||
public static removeOnInsert( | ||
callback: (value: User, reducerEvent: ReducerEvent | undefined) => void | ||
) { | ||
__SPACETIMEDB__.clientDB.getTable("User").removeOnInsert(callback); | ||
} | ||
|
||
public static removeOnUpdate( | ||
callback: ( | ||
oldValue: User, | ||
newValue: User, | ||
reducerEvent: ReducerEvent | undefined | ||
) => void | ||
) { | ||
__SPACETIMEDB__.clientDB.getTable("User").removeOnUpdate(callback); | ||
} | ||
|
||
public static removeOnDelete( | ||
callback: (value: User, reducerEvent: ReducerEvent | undefined) => void | ||
) { | ||
__SPACETIMEDB__.clientDB.getTable("User").removeOnDelete(callback); | ||
} | ||
} | ||
|
||
export default User; | ||
|
||
__SPACETIMEDB__.registerComponent("User", User); |