UNPKG

@bigfishtv/cockpit

Version:

71 lines (60 loc) 2.32 kB
/** * @module Reducers/imageRequestQueue */ import { ENABLE_IMAGE_REQUEST_QUEUE, DISABLE_IMAGE_REQUEST_QUEUE, REQUEST_GENERATED_IMAGE, CANCEL_GENERATED_IMAGE_REQUEST, GENERATED_IMAGE_REQUEST_FULFILLED, } from '../constants/ActionTypes' const MAX_ACTIVE_REQUESTS = 25 const IMAGE_REQUEST_QUEUE_INTERVAL = 50 // ms const IMAGE_REQUEST_INITIAL_DELAY = 250 // ms const IMAGE_REQUEST_TIMEOUT = 5000 // ms const initialState = { queue: [], enabled: false } let queue = [] let pendingAssets = 0 const processQueue = () => { if (!queue.length) return // filter out unresolved requests older than 5 seconds const prePurgeCount = queue.length queue = queue.filter(({ created }) => Date.now() - created < IMAGE_REQUEST_TIMEOUT) const purgeCount = prePurgeCount - queue.length pendingAssets -= purgeCount // if (purgeCount) console.log('Purged ' + purgeCount + ' requests from the queue') // Recheck queue length after oldie purge if (!queue.length) return // Active requests at max, leave it for a tick if (pendingAssets > MAX_ACTIVE_REQUESTS) return // Check if request is too young to be considered yet const actionAge = Date.now() - queue[0].created if (actionAge < IMAGE_REQUEST_INITIAL_DELAY) return const action = queue.shift() if (action.callback) { // console.log('🏁 allowing this asset', action.key) action.callback(action.url) pendingAssets++ } } setInterval(processQueue, IMAGE_REQUEST_QUEUE_INTERVAL) export default function(state = initialState, action) { switch (action.type) { case ENABLE_IMAGE_REQUEST_QUEUE: return { ...state, enabled: true } case DISABLE_IMAGE_REQUEST_QUEUE: return { ...state, enabled: false } case REQUEST_GENERATED_IMAGE: if (state.enabled) queue.push({ ...action, created: Date.now() }) else action.callback(action.url) return { ...state, queue } case GENERATED_IMAGE_REQUEST_FULFILLED: case CANCEL_GENERATED_IMAGE_REQUEST: // if (action.type === GENERATED_IMAGE_REQUEST_FULFILLED) console.log('✅ asset request completed', action.key) // if (action.type === CANCEL_GENERATED_IMAGE_REQUEST) console.log('🗑 cancel loading of this asset', action.key) pendingAssets-- if (state.enabled) queue = queue.filter(item => item.callback !== action.callback) return { ...state, queue } } return { ...state, queue } }