public void TestCursor() { var cache0 = Cache().WithAsync(); cache0.WithAsync().Put(1, new QueryPerson("Ivanov", 30)); IFuture <object> res = cache0.GetFuture <object>(); res.Get(); Cache().Put(1, new QueryPerson("Ivanov", 30)); Cache().Put(1, new QueryPerson("Petrov", 40)); Cache().Put(1, new QueryPerson("Sidorov", 50)); SqlQuery qry = new SqlQuery(typeof(QueryPerson), "age >= 20"); // 1. Test GetAll(). using (IQueryCursor <ICacheEntry <int, QueryPerson> > cursor = Cache().Query(qry)) { cursor.GetAll(); Assert.Throws <InvalidOperationException>(() => { cursor.GetAll(); }); Assert.Throws <InvalidOperationException>(() => { cursor.GetEnumerator(); }); } // 2. Test GetEnumerator. using (IQueryCursor <ICacheEntry <int, QueryPerson> > cursor = Cache().Query(qry)) { cursor.GetEnumerator(); Assert.Throws <InvalidOperationException>(() => { cursor.GetAll(); }); Assert.Throws <InvalidOperationException>(() => { cursor.GetEnumerator(); }); } }
/// <summary> /// Invokes <see cref="IFuture{T}.Get()"/> uninterruptibly. /// </summary> /// <param name="future"> /// The future whose value should be get uninterruptibly.</param> /// <returns>The result of the future computation.</returns> /// <exception cref="ExecutionException"> /// if the computation threw an exception. /// </exception> /// <exception cref="OperationCanceledException"> /// If the current thread was interrupted while waiting. /// </exception> /// <seealso cref="IFuture{T}"/> /// <seealso cref="IFuture{T}.Get()"/> public static T GetUninterruptibly <T>(IFuture <T> future) { bool interrupted = false; try { while (true) { try { return(future.Get()); } catch (ThreadInterruptedException) { interrupted = true; } } } finally { if (interrupted) { Thread.CurrentThread.Interrupt(); } } }
/// <summary> /// Refreshes the value associated with <paramref name="key"/>, unless /// another thread is already doing so. /// </summary> /// <param name="key"> /// The key associated with the value to refresh. /// </param> /// <param name="loader"> /// A <see cref="CacheLoader{T}"/> that is used to refresh the value. /// </param> /// <param name="value"> /// The newly refreshed value associated with <paramref name="key"/> if /// the value was refreshed inline, or the default value of /// <typeparamref name="T"/> if another thread is performing the refresh or /// if a error occurs during refresh. /// </param> /// <returns> /// <c>true</c> if the value was refreshed and <c>false</c> if another /// thread is performing the refresh or if a error has been occured during /// the refresh. /// </returns> bool Refresh(string key, CacheLoader <T> loader, out T value) { LoadingValueReference <T> loading_value_reference = InsertLoadingValueReference(key); value = default(T); if (loading_value_reference == null) { return(false); } IFuture <T> result = LoadAsync(key, loading_value_reference, loader); if (result.IsCompleted) { try { value = result.Get(); } catch { // don't let refresh exceptions propagate; error was already logged. } } return(false); }
public static Task <TResult?> AsTask <TResult>(this IFuture future, CancellationToken cancellationToken = default) where TResult : Java.Lang.Object { cancellationToken.Register(() => future.Cancel(true)); return(Task.Run(() => { try { var obj = future.Get(); if (future.IsCancelled || cancellationToken.IsCancellationRequested) { throw new OperationCanceledException(); } return (TResult?)obj; } catch (CancellationException) { throw new OperationCanceledException(); } })); }