private void HandleRequest(Guid assetId, AssetRequest.AssetRequestHandler handler, AssetRequest.AssetErrorHandler errHandler) { var reader = ConfigSingleton.ChattelReader; if (reader == null) { // There's no Chattel. Fail. errHandler(new AssetError { Error = AssetErrorType.ConfigIncorrect, Message = "Chattel was null!", }); return; } reader.GetAssetAsync(assetId, asset => { if (asset == null) { errHandler(new AssetError { Error = AssetErrorType.AssetIdUnknown, Message = $"Could not find any asset with ID {assetId}", }); return; } if (!ConfigSingleton.ValidTypes.Contains(asset.Type)) { errHandler(new AssetError { Error = AssetErrorType.AssetTypeWrong, }); return; } handler(asset); }); }
public void RequestMeshAssetOnCap(Guid capId, Guid assetId, AssetRequest.AssetRequestHandler handler, AssetRequest.AssetErrorHandler errHandler) { handler = handler ?? throw new ArgumentNullException(nameof(handler)); errHandler = errHandler ?? throw new ArgumentNullException(nameof(errHandler)); if (_negativeCache != null) { _negativeCacheLock.EnterReadLock(); var negCacheContainsId = false; try { negCacheContainsId = _negativeCache.Contains(assetId.ToString("N")); } finally { _negativeCacheLock.ExitReadLock(); } if (negCacheContainsId) { errHandler(new AssetError { Error = AssetErrorType.AssetTypeWrong, }); return; } } if (_caps.TryGetValue(capId, out Capability cap)) { cap.RequestAsset( assetId, (asset) => { if (!ConfigSingleton.ValidTypes.Any(type => type == asset.Type)) { if (_negativeCache != null) { _negativeCacheLock.EnterWriteLock(); try { _negativeCache.Set(new System.Runtime.Caching.CacheItem(assetId.ToString("N"), 0), _negativeCachePolicy); } finally { _negativeCacheLock.ExitWriteLock(); } } errHandler(new AssetError { Error = AssetErrorType.AssetTypeWrong, }); } if (asset.Type == 49) { handler(asset); } else { errHandler(new AssetError { Error = AssetErrorType.AssetTypeWrong, }); } }, errHandler ); return; } errHandler(new AssetError { Error = AssetErrorType.CapabilityIdUnknown, }); }
public void RequestAsset(Guid assetId, AssetRequest.AssetRequestHandler handler, AssetRequest.AssetErrorHandler errHandler) { if (!IsActive) // Paused { AssetRequest requestToProcess = null; var gotLock = false; try { // Skiplock: Only locking because of possible shutdown action. Monitor.TryEnter(_requests, ref gotLock); if (gotLock) { _requests.Enqueue(new AssetRequest(assetId, handler, errHandler)); if (_requests.Count > MAX_QUEUED_REQUESTS) { _requests.TryDequeue(out requestToProcess); } } } finally { if (gotLock) { Monitor.Exit(_requests); } } var errors = new Queue <Exception>(); // Have to make sure both operations below happen, even if they throw. if (!gotLock) { // It seems that this cap cannot queue the request. Probably shutting down. Tell the client no such luck. try { errHandler(new AssetError { Error = AssetErrorType.QueueFilled, }); } catch (Exception e) { errors.Enqueue(e); } } try { requestToProcess?.Respond(new AssetError { Error = AssetErrorType.QueueFilled, }); } catch (Exception e) { errors.Enqueue(e); } if (errors.Count > 0) { throw new AggregateException(errors); } return; } // Not paused, query Chattel. HandleRequest(assetId, handler, errHandler); }