import { API } from '../core/api' ; import { streamHandler } from '../helpers/handlers' ; import { QueryResult , Thread } from '../models' ; import { ReadableStream } from 'web-streams-polyfill/ponyfill' ; extends API export default class Snapshots extends API { returns async create ( ) { const response = await this . sendPost ( 'snapshots' ) ; return response . status === 201 ; } param wait returns async search ( wait ? ) { const response = await this . sendPost ( 'snapshots/search' , undefined , { wait : wait || 2 } ) ; if ( ! response . body ) { throw Error ( 'Empty response stream' ) ; } return streamHandler < QueryResult > ( response . body as ReadableStream ) ; } param id param wait returns async apply ( id ? , wait ? ) { const stream = await this . search ( wait ) ; let isReader ; let cancellationRequest = false ; const self = this ; return new ReadableStream < QueryResult > ( { start ( controller ) { const reader = stream . getReader ( ) ; isReader = reader ; const processResult = ( result ) => { if ( result . done ) { if ( cancellationRequest ) { return ; } controller . close ( ) ; return ; } try { if ( id === undefined || result . value . id === id ) { self . applySnapshot ( result . value ) . then ( ( success ) => { if ( success ) { controller . enqueue ( result . value ) ; } else { throw new Error ( 'Unable to apply snapshot' ) ; } } ) ; } } catch ( e ) { controller . error ( e ) ; cancellationRequest = true ; reader . cancel ( undefined ) ; return ; } reader . read ( ) . then ( processResult ) ; } ; reader . read ( ) . then ( processResult ) ; } , cancel ( reason ? ) { cancellationRequest = true ; isReader . cancel ( reason ) ; } } ) ; } async applySnapshot ( snapshot ) { const snap = snapshot . value ; const response = await this . sendPut ( `threads/${ snap . id }` , undefined , undefined , snap ) ; return response . status === 204 ; } }