public async Task<ActionResult> Collect()
 {
     var visit = new Visit {IP = IPAddress.Parse(Request.UserHostAddress).MapToIPv4(), Timestamp = DateTime.UtcNow};
     await GeoLocator.Instance.Locate(visit);
     await StorageService.Instance.StoreVisit(visit);
     return Content("OK");
 }
        public async Task Locate(Visit visit)
        {
            var addr = visit.IP;
            int l = 0, h = _countryInfos.Count - 1, m = 0;
            bool found = false;
            while (h - l > 1)
            {
                m = (l + h)/2;
                var comparisonRes = _countryInfos[m].CompareWithRange(addr);
                if (comparisonRes == 0)
                {
                    found = true;
                    break;
                }
                else if (comparisonRes < 0) h = m;
                else l = m;
            }
            if (!found)
            {
                if (_countryInfos[l].CompareWithRange(addr) == 0)
                {
                    found = true;
                    m = l;
                }
                else if (_countryInfos[h].CompareWithRange(addr) == 0)
                {
                    found = true;
                    m = h;
                }
#if DEBUG
                else
                {
                    found = true;
                    m = 70; // ukraine
                }
#endif
        }

            if (found)
            {
                visit.Country = _countryInfos[m].Name;
                visit.CountryCode = _countryInfos[m].Code;
            }
        }
 public async Task StoreVisit(Visit visit)
 {
     await _connection.AppendToStreamAsync("Visits", -2, new IEvent[] { visit });
 }