private async Task JoinZone(int zonePosition) { for (int i = 0; i < 5; i++) { try { this.Logger?.LogMessage($"{{action}}Joining {{zone}}zone {zonePosition}{{action}}..."); var stopwatch = new Stopwatch(); stopwatch.Start(); await SaliensApi.JoinZoneAsync(this.Token, zonePosition); stopwatch.Stop(); var startDate = DateTime.Now; // If the request took too long, resynchronize the start date if (stopwatch.Elapsed > TimeSpan.FromSeconds(1)) { var playerInfo = await SaliensApi.GetPlayerInfoAsync(this.Token, TimeSpan.FromSeconds(0)); var diff = (startDate - (DateTime.Now - playerInfo.TimeInZone)); if (diff > TimeSpan.FromSeconds(0)) { this.Logger?.LogMessage($"{{action}}Recalibrated zone join time with {{value}}{diff.Negate().TotalSeconds.ToString("0.###")} seconds"); startDate = DateTime.Now - playerInfo.TimeInZone; } } // States this.ActiveZone = this.ActivePlanet.Zones[zonePosition]; this.ActiveZoneStartDate = startDate; this.PlayerInfo.ActiveZoneGame = this.ActiveZone.GameId; this.PlayerInfo.ActiveZonePosition = zonePosition.ToString(); this.PlayerInfo.TimeInZone = TimeSpan.FromSeconds(0); this.State = BotState.InZone; this.PresenceUpdateTrigger.SetSaliensPlayerState(this.PlayerInfo); return; } catch (SaliensApiException ex) { switch (ex.EResult) { case EResult.Fail: case EResult.Busy: case EResult.RateLimitExceeded: this.Logger?.LogMessage($"{{warn}}Failed to join zone: {ex.Message} - Giving it a few seconds ({i + 1}/5)..."); await Task.Delay(2000); continue; case EResult.Expired: case EResult.NoMatch: default: this.Logger?.LogMessage($"{{warn}}Failed to join zone: {ex.Message}"); ResetState(); throw; } } catch (WebException ex) { this.Logger?.LogMessage($"{{warn}}Failed to join zone: {ex.Message} - Giving it a few seconds ({i + 1}/5)..."); await Task.Delay(2000); continue; } } // States, only set when failed ResetState(); void ResetState() { this.State = BotState.OnPlanet; } }