use of com.koushikdutta.async.future.SimpleFuture in project AndroidAsync by koush.
the class AsyncSocketMiddleware method getSocket.
@Override
public Cancellable getSocket(final GetSocketData data) {
final Uri uri = data.request.getUri();
final int port = getSchemePort(data.request.getUri());
if (port == -1) {
return null;
}
data.state.put("socket-owner", this);
final String lookup = computeLookup(uri, port, data.request.getProxyHost(), data.request.getProxyPort());
ConnectionInfo info = getOrCreateConnectionInfo(lookup);
synchronized (AsyncSocketMiddleware.this) {
if (info.openCount >= maxConnectionCount) {
// wait for a connection queue to free up
SimpleCancellable queueCancel = new SimpleCancellable();
info.queue.add(data);
return queueCancel;
}
info.openCount++;
while (!info.sockets.isEmpty()) {
IdleSocketHolder idleSocketHolder = info.sockets.pop();
final AsyncSocket socket = idleSocketHolder.socket;
if (idleSocketHolder.idleTime + idleTimeoutMs < System.currentTimeMillis()) {
socket.setClosedCallback(null);
socket.close();
continue;
}
if (!socket.isOpen())
continue;
data.request.logd("Reusing keep-alive socket");
data.connectCallback.onConnectCompleted(null, socket);
// just a noop/dummy, as this can't actually be cancelled.
SimpleCancellable ret = new SimpleCancellable();
ret.setComplete();
return ret;
}
}
if (!connectAllAddresses || proxyHost != null || data.request.getProxyHost() != null) {
// just default to connecting to a single address
data.request.logd("Connecting socket");
String unresolvedHost;
int unresolvedPort;
boolean proxied = false;
if (data.request.getProxyHost() == null && proxyHost != null)
data.request.enableProxy(proxyHost, proxyPort);
if (data.request.getProxyHost() != null) {
unresolvedHost = data.request.getProxyHost();
unresolvedPort = data.request.getProxyPort();
proxied = true;
} else {
unresolvedHost = uri.getHost();
unresolvedPort = port;
}
if (proxied) {
data.request.logv("Using proxy: " + unresolvedHost + ":" + unresolvedPort);
}
return mClient.getServer().connectSocket(unresolvedHost, unresolvedPort, wrapCallback(data, uri, port, proxied, data.connectCallback));
}
// try to connect to everything...
data.request.logv("Resolving domain and connecting to all available addresses");
final SimpleFuture<AsyncSocket> checkedReturnValue = new SimpleFuture<>();
Future<AsyncSocket> socket = mClient.getServer().getAllByName(uri.getHost()).then(addresses -> Futures.loopUntil(addresses, address -> {
SimpleFuture<AsyncSocket> loopResult = new SimpleFuture<>();
final String inetSockAddress = String.format(Locale.ENGLISH, "%s:%s", address, port);
data.request.logv("attempting connection to " + inetSockAddress);
mClient.getServer().connectSocket(new InetSocketAddress(address, port), loopResult::setComplete);
return loopResult;
})).fail(e -> wrapCallback(data, uri, port, false, data.connectCallback).onConnectCompleted(e, null));
checkedReturnValue.setComplete(socket).setCallback((e, successfulSocket) -> {
if (successfulSocket == null)
return;
// The exception value will only ever be a CancellationException.
if (e == null) {
// handle successes here (wrap the callback)
wrapCallback(data, uri, port, false, data.connectCallback).onConnectCompleted(null, successfulSocket);
return;
}
data.request.logd("Recycling extra socket leftover from cancelled operation");
idleSocket(successfulSocket);
recycleSocket(successfulSocket, data.request);
});
return checkedReturnValue;
}
use of com.koushikdutta.async.future.SimpleFuture in project ion by koush.
the class FileLoader method loadBitmap.
@Override
public Future<BitmapInfo> loadBitmap(final Context context, final Ion ion, final String key, final String uri, final int resizeWidth, final int resizeHeight, final boolean animateGif) {
if (uri == null || !uri.startsWith("file:/"))
return null;
final SimpleFuture<BitmapInfo> ret = new SimpleFuture<BitmapInfo>();
// Log.d("FileLoader", "Loading file bitmap " + uri + " " + resizeWidth + "," + resizeHeight);
Ion.getBitmapLoadExecutorService().execute(new Runnable() {
@Override
public void run() {
if (ret.isCancelled()) {
// Log.d("FileLoader", "Bitmap load cancelled (no longer needed)");
return;
}
try {
File file = new File(URI.create(uri));
BitmapFactory.Options options = ion.getBitmapCache().prepareBitmapOptions(file, resizeWidth, resizeHeight);
Point size = new Point(options.outWidth, options.outHeight);
BitmapInfo info;
if (animateGif && TextUtils.equals("image/gif", options.outMimeType)) {
FileInputStream fin = new FileInputStream(file);
try {
info = loadGif(key, size, fin, options);
} finally {
StreamUtility.closeQuietly(fin);
}
} else {
Bitmap bitmap = IonBitmapCache.loadBitmap(file, options);
if (bitmap == null)
throw new Exception("Bitmap failed to load");
info = new BitmapInfo(key, options.outMimeType, bitmap, size);
}
info.servedFrom = ResponseServedFrom.LOADED_FROM_CACHE;
ret.setComplete(info);
} catch (OutOfMemoryError e) {
ret.setComplete(new Exception(e), null);
} catch (Exception e) {
ret.setComplete(e);
}
}
});
return ret;
}
use of com.koushikdutta.async.future.SimpleFuture in project ion by koush.
the class ResourceLoader method loadBitmap.
@Override
public Future<BitmapInfo> loadBitmap(final Context context, final Ion ion, final String key, final String uri, final int resizeWidth, final int resizeHeight, final boolean animateGif) {
if (uri == null || !uri.startsWith("android.resource:/"))
return null;
final SimpleFuture<BitmapInfo> ret = new SimpleFuture<BitmapInfo>();
// Log.d("FileLoader", "Loading file bitmap " + uri + " " + resizeWidth + "," + resizeHeight);
Ion.getBitmapLoadExecutorService().execute(new Runnable() {
@Override
public void run() {
try {
Resource res = lookupResource(context, uri);
BitmapFactory.Options options = ion.getBitmapCache().prepareBitmapOptions(res.res, res.id, resizeWidth, resizeHeight);
Point size = new Point(options.outWidth, options.outHeight);
BitmapInfo info;
if (animateGif && TextUtils.equals("image/gif", options.outMimeType)) {
InputStream in = res.res.openRawResource(res.id);
try {
info = loadGif(key, size, in, options);
} finally {
StreamUtility.closeQuietly(in);
}
} else {
Bitmap bitmap = IonBitmapCache.loadBitmap(res.res, res.id, options);
if (bitmap == null)
throw new Exception("Bitmap failed to load");
info = new BitmapInfo(key, options.outMimeType, bitmap, size);
}
info.servedFrom = ResponseServedFrom.LOADED_FROM_CACHE;
ret.setComplete(info);
} catch (OutOfMemoryError e) {
ret.setComplete(new Exception(e), null);
} catch (Exception e) {
ret.setComplete(e);
}
}
});
return ret;
}
use of com.koushikdutta.async.future.SimpleFuture in project ion by koush.
the class StreamLoader method loadBitmap.
@Override
public Future<BitmapInfo> loadBitmap(final Context context, final Ion ion, final String key, final String uri, final int resizeWidth, final int resizeHeight, final boolean animateGif) {
final SimpleFuture<BitmapInfo> ret = new SimpleFuture<BitmapInfo>();
// Log.d("FileLoader", "Loading file bitmap " + uri + " " + resizeWidth + "," + resizeHeight);
Ion.getBitmapLoadExecutorService().execute(new Runnable() {
@Override
public void run() {
InputStream in = null;
try {
in = getInputStream(context, uri);
BitmapFactory.Options options = ion.getBitmapCache().prepareBitmapOptions(in, resizeWidth, resizeHeight);
StreamUtility.closeQuietly(in);
Point size = new Point(options.outWidth, options.outHeight);
BitmapInfo info;
in = getInputStream(context, uri);
if (animateGif && TextUtils.equals("image/gif", options.outMimeType)) {
info = loadGif(key, size, in, options);
} else {
Bitmap bitmap = IonBitmapCache.loadBitmap(in, options);
if (bitmap == null)
throw new Exception("Bitmap failed to load");
info = new BitmapInfo(key, options.outMimeType, bitmap, size);
}
info.servedFrom = ResponseServedFrom.LOADED_FROM_CACHE;
ret.setComplete(info);
} catch (OutOfMemoryError e) {
ret.setComplete(new Exception(e), null);
} catch (Exception e) {
ret.setComplete(e);
} finally {
StreamUtility.closeQuietly(in);
}
}
});
return ret;
}
use of com.koushikdutta.async.future.SimpleFuture in project ion by koush.
the class PackageIconLoader method loadBitmap.
@Override
public Future<BitmapInfo> loadBitmap(Context context, final Ion ion, final String key, final String uri, int resizeWidth, int resizeHeight, boolean animateGif) {
if (uri == null || !uri.startsWith("package:"))
return null;
final SimpleFuture<BitmapInfo> ret = new SimpleFuture<BitmapInfo>();
Ion.getBitmapLoadExecutorService().execute(new Runnable() {
@Override
public void run() {
try {
final URI request = URI.create(uri);
String pkg = request.getHost();
PackageManager pm = ion.getContext().getPackageManager();
Bitmap bmp = ((BitmapDrawable) pm.getPackageInfo(pkg, 0).applicationInfo.loadIcon(pm)).getBitmap();
if (bmp == null)
throw new Exception("package icon failed to load");
BitmapInfo info = new BitmapInfo(key, null, bmp, new Point(bmp.getWidth(), bmp.getHeight()));
info.servedFrom = ResponseServedFrom.LOADED_FROM_CACHE;
ret.setComplete(info);
} catch (Exception e) {
ret.setComplete(e);
}
}
});
return ret;
}
Aggregations