@file:JvmName("PromiseUtilities") package org.session.libsignal.utilities import nl.komponents.kovenant.Promise import nl.komponents.kovenant.deferred import nl.komponents.kovenant.task import java.util.concurrent.TimeoutException fun emptyPromise() = EMPTY_PROMISE private val EMPTY_PROMISE: Promise<*, java.lang.Exception> = task {} fun Promise.get(defaultValue: V): V { return try { get() } catch (e: Exception) { defaultValue } } fun Promise.recover(callback: (exception: E) -> V): Promise { val deferred = deferred() success { deferred.resolve(it) }.fail { try { val value = callback(it) deferred.resolve(value) } catch (e: Throwable) { deferred.reject(it) } } return deferred.promise } fun Promise.successBackground(callback: (value: V) -> Unit): Promise { ThreadUtils.queue { try { callback(get()) } catch (e: Exception) { Log.d("Loki", "Failed to execute task in background: ${e.message}.") } } return this } fun Promise.timeout(millis: Long): Promise { if (this.isDone()) { return this; } val deferred = deferred() ThreadUtils.queue { Thread.sleep(millis) if (!deferred.promise.isDone()) { deferred.reject(TimeoutException("Promise timed out.")) } } this.success { if (!deferred.promise.isDone()) { deferred.resolve(it) } }.fail { if (!deferred.promise.isDone()) { deferred.reject(it) } } return deferred.promise }