public void Perform(SeedAtlanticOcean job)
        {
            var reportBuilder = new WorkReportBuilder("Seed Atlantic Ocean");

            try
            {
                var atlantics = _queryProcessor.Execute(new PlacesWithName
                {
                    MaxResults        = 5,
                    Term              = AtlanticOceanText,
                    TermMatchStrategy = StringMatchStrategy.Equals,
                });
                if (atlantics.Any())
                {
                    reportBuilder.Report("At least {0} Place(s) named '{1}' already exist(s).", atlantics.Count(), AtlanticOceanText);
                }
                else
                {
                    reportBuilder.Report("There are no Places named '{0}'.", AtlanticOceanText);
                    reportBuilder.Report("Seeding '{0}'.", AtlanticOceanText);

                    var geoPlanetPlaces   = _geoPlanet.Places(AtlanticOceanText);
                    var geoPlanetToponyms = _geoNames.Search(new SearchOptions(SearchType.NameEquals, AtlanticOceanText));

                    var geoNamesToponym = geoPlanetToponyms.FirstOrDefault(x => x.FeatureClassCode == "H");
                    var geoPlanetPlace  = geoPlanetPlaces.FirstOrDefault(x => x.Type.Code == 37 || x.Type.Code == 38);

                    if (geoPlanetPlace != null && geoNamesToponym != null)
                    {
                        _queryProcessor.Execute(new PlaceByWoeId(geoPlanetPlace.WoeId, geoNamesToponym.GeoNameId));
                    }

                    reportBuilder.Report("There is/are now {0} Place(s) named '{1}'.", atlantics.Count(), AtlanticOceanText);
                }
            }
            catch (Exception ex)
            {
                reportBuilder.Report("");
                reportBuilder.Report("JOB FAILED!");
                reportBuilder.Report(ex.GetType().Name);
                reportBuilder.Report(ex.Message);
                reportBuilder.Report(ex.StackTrace);
                _exceptionLogger.Log(ex);
            }
            finally
            {
                reportBuilder.Send(_mailSender);
            }
        }
Example #2
0
        internal static int Handle(WoeIdByCoordinates query, IContainGeoNames geoNamesContainer, IContainGeoPlanet geoPlanetContainer)
        {
            if (!query.Coordinates.Latitude.HasValue)
            {
                throw new ArgumentException("Query's Coordinates.Latitude is null.");
            }
            if (!query.Coordinates.Longitude.HasValue)
            {
                throw new ArgumentException("Query's Coordinates.Longitude is null.");
            }

            int?woeId = null;

            // first, invoke geonames geocoder
            var retryCount = 0;
            IEnumerable <Toponym> geoNames = null;

            while (geoNames == null && retryCount < 6)
            {
                ++retryCount;
                geoNames = geoNamesContainer.FindNearbyPlaceName(new NearbyPlaceNameFinder
                {
                    Latitude  = query.Coordinates.Latitude.Value,
                    Longitude = query.Coordinates.Longitude.Value,
                    Language  = "en",
                });
            }
            if (geoNames == null)
            {
                throw new ApplicationException("Querying GeoNames service resulted in null result.");
            }
            geoNames = geoNames.ToArray();

            foreach (var geoName in geoNames)
            {
                // try to concord with woeid
                var concordance = geoPlanetContainer.Concordance(ConcordanceNamespace.GeoNames, geoName.GeoNameId);
                if (concordance == null || concordance.WoeId <= 0)
                {
                    continue;
                }

                // make sure place exists
                var geoPlanetPlace = geoPlanetContainer.Place(concordance.WoeId);
                if (geoPlanetPlace == null)
                {
                    continue;
                }

                woeId = concordance.WoeId;
                break;
            }

            // if there is still no WOE ID, try a textual search
            if (!woeId.HasValue)
            {
                foreach (var geoName in geoNames)
                {
                    var searchText = new StringBuilder(geoName.Name);
                    if (!string.IsNullOrWhiteSpace(geoName.Admin3Name))
                    {
                        searchText.Append(" " + geoName.Admin3Name);
                    }
                    if (!string.IsNullOrWhiteSpace(geoName.Admin2Name))
                    {
                        searchText.Append(" " + geoName.Admin2Name);
                    }
                    if (!string.IsNullOrWhiteSpace(geoName.Admin1Name))
                    {
                        searchText.Append(" " + geoName.Admin1Name);
                    }
                    searchText.Append(", " + geoName.CountryName);

                    var geoPlanetPlaces = geoPlanetContainer.Places(searchText.ToString().Replace("/", "-"))
                                          .Where(x => x.WoeId > 0).ToArray();

                    NGeo.Yahoo.GeoPlanet.Place geoPlanetPlace = null;
                    if (geoPlanetPlaces.Length == 1)
                    {
                        geoPlanetPlace = geoPlanetPlaces.Single();
                    }
                    else if (geoPlanetPlaces.Length > 1)
                    {
                        // when multiple results are found, pick the one with
                        // the closest lat & lng match
                        var gn = geoName;
                        Func <NGeo.Yahoo.GeoPlanet.Place, double> coordinateComparer = x =>
                        {
                            // is this lat/lng greater or less than the geonames lat/lng?
                            var latDiff = x.Center.Latitude > gn.Latitude ? x.Center.Latitude - gn.Latitude : gn.Latitude - x.Center.Latitude;
                            var lngDiff = x.Center.Longitude > gn.Longitude ? x.Center.Longitude - gn.Longitude : gn.Longitude - x.Center.Longitude;
                            return(latDiff + lngDiff);
                        };
                        var closest    = geoPlanetPlaces.OrderBy(coordinateComparer).ToArray();
                        var separation = closest.Select(coordinateComparer).First();
                        if (separation < 1)
                        {
                            geoPlanetPlace = closest.First();
                        }
                    }

                    if (geoPlanetPlace != null)
                    {
                        woeId = geoPlanetPlace.WoeId;
                    }
                }
            }

            return(woeId.HasValue
                ? woeId.Value
                : GeoPlanetPlace.EarthWoeId);
        }