refactor: store w transaction

This commit is contained in:
Andres Aya
2023-04-20 08:14:11 -05:00
parent 28be45a9b4
commit 2b27416af0
2 changed files with 23 additions and 28 deletions

View File

@@ -82,7 +82,7 @@ export type SignalKeyStore = {
export type SignalKeyStoreWithTransaction = SignalKeyStore & { export type SignalKeyStoreWithTransaction = SignalKeyStore & {
isInTransaction: () => boolean isInTransaction: () => boolean
transaction(exec: () => Promise<void>): Promise<void> transaction<T>(exec: () => Promise<T>): Promise<T>
} }
export type TransactionCapabilityOptions = { export type TransactionCapabilityOptions = {
@@ -92,7 +92,7 @@ export type TransactionCapabilityOptions = {
export type SignalAuthState = { export type SignalAuthState = {
creds: SignalCreds creds: SignalCreds
keys: SignalKeyStore keys: SignalKeyStore | SignalKeyStoreWithTransaction
} }
export type AuthenticationState = { export type AuthenticationState = {

View File

@@ -93,11 +93,9 @@ export const addTransactionCapability = (
let transactionCache: SignalDataSet = { } let transactionCache: SignalDataSet = { }
let mutations: SignalDataSet = { } let mutations: SignalDataSet = { }
/** return {
* prefetches some data and stores in memory, get: async(type, ids) => {
* useful if these data points will be used together often if(inTransaction) {
* */
const prefetch = async<T extends keyof SignalDataTypeMap>(type: T, ids: string[]) => {
const dict = transactionCache[type] const dict = transactionCache[type]
const idsRequiringFetch = dict const idsRequiringFetch = dict
? ids.filter(item => typeof dict[item] !== 'undefined') ? ids.filter(item => typeof dict[item] !== 'undefined')
@@ -108,17 +106,12 @@ export const addTransactionCapability = (
const result = await state.get(type, idsRequiringFetch) const result = await state.get(type, idsRequiringFetch)
transactionCache[type] ||= {} transactionCache[type] ||= {}
transactionCache[type] = Object.assign( Object.assign(
transactionCache[type]!, transactionCache[type]!,
result result
) )
} }
}
return {
get: async(type, ids) => {
if(inTransaction) {
await prefetch(type, ids)
return ids.reduce( return ids.reduce(
(dict, id) => { (dict, id) => {
const value = transactionCache[type]?.[id] const value = transactionCache[type]?.[id]
@@ -148,16 +141,17 @@ export const addTransactionCapability = (
} }
}, },
isInTransaction: () => inTransaction, isInTransaction: () => inTransaction,
transaction: async(work) => { async transaction(work) {
let result: Awaited<ReturnType<typeof work>>
// if we're already in a transaction, // if we're already in a transaction,
// just execute what needs to be executed -- no commit required // just execute what needs to be executed -- no commit required
if(inTransaction) { if(inTransaction) {
await work() result = await work()
} else { } else {
logger.trace('entering transaction') logger.trace('entering transaction')
inTransaction = true inTransaction = true
try { try {
await work() result = await work()
if(Object.keys(mutations).length) { if(Object.keys(mutations).length) {
logger.trace('committing transaction') logger.trace('committing transaction')
// retry mechanism to ensure we've some recovery // retry mechanism to ensure we've some recovery
@@ -184,6 +178,7 @@ export const addTransactionCapability = (
dbQueriesInTransaction = 0 dbQueriesInTransaction = 0
} }
} }
return result
} }
} }
} }