private IEnumerator ProcessBulkedRequests() { while (true) { //Debug.Log(DateTime.UtcNow + ": Checking bulked requests"); // When available, authorized, and root context is restored try to send out chunks if (IsAvailable && Authorized && _authorizationContext.Status != RDataContextStatus.Interrupted) { bool hasErrors = false; var localDataChunks = LocalDataRepository.LoadDataChunksJson(UserId); if (localDataChunks != null) { foreach (var chunk in localDataChunks) { if (RData.RDataLogging.DoLog) { Debug.Log(DateTime.UtcNow + ": Sending the chunk " + chunk.requestId); } yield return(CoroutineManager.StartCoroutine(JsonRpcClient.SendJson <BooleanResponse>(chunk.requestJson, chunk.requestId, (response) => { if (RData.RDataLogging.DoLog) { Debug.Log(DateTime.UtcNow + ": Sent the chunk " + chunk.requestId); } if (response.Result) { LocalDataRepository.RemoveDataChunk(UserId, chunk.requestId); // At this point we received a positive answer from the server } // Most realistic scenario here is if (response.HasError) { if (response.Error.Data == kContextValidationError) { // This is a very specific case that happens when we are trying to re-send a chunk with context operations after that context was closed. // This means this chunk was already received by the server and we can safely delete it. LocalDataRepository.RemoveDataChunk(UserId, chunk.requestId); if (RData.RDataLogging.DoError) { Debug.LogError("Context validation error. This chunk was already received by the server. Deletting the chunk"); } } else { hasErrors = true; } } }))); // If any unknown errors happened this means that most likely something horribly wrong with the server. // Let's take some timeout to prevent spamming it if (hasErrors) { if (RData.RDataLogging.DoLog) { Debug.Log(DateTime.UtcNow + ": Unknown error happened, waiting for " + kTimeoutAfterError + " seconds"); } yield return(new WaitForSeconds(kTimeoutAfterError)); } } } // Check if the current chunk has items and expired. If so, save and refresh it if (_activeChunk.Length > 0 && DateTime.UtcNow > Tools.Time.UnixTimeMillisecondsToDateTime(_activeChunk.CreatedAt) + TimeSpan.FromSeconds(ChunkLifeTime)) { ResetActiveChunk(); } } yield return(null); } }