feat: add models package
This commit is contained in:
90
packages/models/src/Domain/Runtime/Deltas/FileImport.ts
Normal file
90
packages/models/src/Domain/Runtime/Deltas/FileImport.ts
Normal file
@@ -0,0 +1,90 @@
|
||||
import { ImmutablePayloadCollection } from '../Collection/Payload/ImmutablePayloadCollection'
|
||||
import { ConflictDelta } from './Conflict'
|
||||
import { DecryptedPayloadInterface } from '../../Abstract/Payload/Interfaces/DecryptedPayload'
|
||||
import { DeletedPayloadInterface, isDecryptedPayload, PayloadEmitSource } from '../../Abstract/Payload'
|
||||
import { HistoryMap } from '../History'
|
||||
import { extendSyncDelta, SourcelessSyncDeltaEmit, SyncDeltaEmit } from './Abstract/DeltaEmit'
|
||||
import { DeltaInterface } from './Abstract/DeltaInterface'
|
||||
import { SyncResolvedPayload } from './Utilities/SyncResolvedPayload'
|
||||
import { getIncrementedDirtyIndex } from '../DirtyCounter/DirtyCounter'
|
||||
|
||||
export class DeltaFileImport implements DeltaInterface {
|
||||
constructor(
|
||||
readonly baseCollection: ImmutablePayloadCollection,
|
||||
private readonly applyPayloads: DecryptedPayloadInterface[],
|
||||
protected readonly historyMap: HistoryMap,
|
||||
) {}
|
||||
|
||||
public result(): SyncDeltaEmit {
|
||||
const result: SyncDeltaEmit = {
|
||||
emits: [],
|
||||
ignored: [],
|
||||
source: PayloadEmitSource.FileImport,
|
||||
}
|
||||
|
||||
for (const payload of this.applyPayloads) {
|
||||
const resolved = this.resolvePayload(payload, result)
|
||||
|
||||
extendSyncDelta(result, resolved)
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
private resolvePayload(
|
||||
payload: DecryptedPayloadInterface | DeletedPayloadInterface,
|
||||
currentResults: SyncDeltaEmit,
|
||||
): SourcelessSyncDeltaEmit {
|
||||
/**
|
||||
* Check to see if we've already processed a payload for this id.
|
||||
* If so, that would be the latest value, and not what's in the base collection.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Find the most recently created conflict if available, as that
|
||||
* would contain the most recent value.
|
||||
*/
|
||||
let current = currentResults.emits.find((candidate) => {
|
||||
return isDecryptedPayload(candidate) && candidate.content.conflict_of === payload.uuid
|
||||
})
|
||||
|
||||
/**
|
||||
* If no latest conflict, find by uuid directly.
|
||||
*/
|
||||
if (!current) {
|
||||
current = currentResults.emits.find((candidate) => {
|
||||
return candidate.uuid === payload.uuid
|
||||
})
|
||||
}
|
||||
|
||||
/**
|
||||
* If not found in current results, use the base value.
|
||||
*/
|
||||
if (!current) {
|
||||
const base = this.baseCollection.find(payload.uuid)
|
||||
if (base && isDecryptedPayload(base)) {
|
||||
current = base as SyncResolvedPayload
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* If the current doesn't exist, we're creating a new item from payload.
|
||||
*/
|
||||
if (!current) {
|
||||
return {
|
||||
emits: [
|
||||
payload.copyAsSyncResolved({
|
||||
dirty: true,
|
||||
dirtyIndex: getIncrementedDirtyIndex(),
|
||||
lastSyncEnd: new Date(0),
|
||||
}),
|
||||
],
|
||||
ignored: [],
|
||||
}
|
||||
}
|
||||
|
||||
const delta = new ConflictDelta(this.baseCollection, current, payload, this.historyMap)
|
||||
|
||||
return delta.result()
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user