org.hd.d.pg2k.svrCore.location
Class GeoUtils

java.lang.Object
  extended by org.hd.d.pg2k.svrCore.location.GeoUtils

public final class GeoUtils
extends java.lang.Object

Geographical-related utility functions. This contains utilities, for example, to guess the approximate geographical location of an HTTP client from its IP address.


Nested Class Summary
static class GeoUtils.CCTLD
          An immutable DNS ccTLD (two-letter) country code.
 
Field Summary
private static java.lang.String BUNDLE_NAME_DEFAULT_CCTLD_FROM_IP_PREFIX
          The base name of the default IP-to-location bundle.
private static java.lang.String BUNDLE_NAME_DEFAULT_GEO_PROXIMITY
          The base name of the default geographic proximity bundle.
private static java.util.SortedMap<AddrTools.AddrPrefix,java.lang.String> ccTLDFromIPPrefix
          Cached immutable default ccTLD-from-IP-prefix SortedMap, or empty if none.
private static int ccTLDFromIPPrefixLongestKey
          Longest key in octets in ccTLDFromIPPrefix; non-negative.
private static int DEFAULT_MAX_OCTETS_LOOKUP
          Default maximum prefix octets to look up in registry; strictly positive.
private static java.util.Map<GeoUtils.CCTLD,java.util.Set<GeoUtils.CCTLD>> defaultGeoMap
          Immutable Map for default proximity from CCTLD to Set of all neighbours.
 
Constructor Summary
private GeoUtils()
          Prevent construction of an instance.
 
Method Summary
static GeoProximity computeProximity(java.lang.String region1, GeoUtils.CCTLD host2CC)
          Compute approximate proximity of a host in a given region to a given country; never null.
static GeoProximity computeProximityByAddress(java.net.InetAddress host1, GeoUtils.CCTLD host2CC, boolean quick)
          Compute approximate proximity of one host to a given country.
static GeoUtils.CCTLD getCCTLDByAddress(java.net.InetAddress addr, boolean quick)
          Guess geographical "location" of given IP address (usually of an HTTP client).
static java.util.SortedMap<AddrTools.AddrPrefix,java.lang.String> getCCTLDFromIPPrefix()
          Get built-in immutable IPv4-to-ccTLD map; never null.
static java.util.Set<GeoUtils.CCTLD> getCloseCCTLDs(GeoUtils.CCTLD ccTLD)
          Get geographically-close ccTLDs to the specified ccTLD; empty if none, but never null.
static java.util.Set<GeoUtils.CCTLD> getCountriesInRegion(java.lang.String region)
          Get ccTLDs in the specified region; empty if none, but never null.
static java.lang.String getRegionByAddress(java.net.InetAddress addr, boolean quick)
          Guess country or geographic region of IP address; never returns null nor "".
static boolean isSyntaticallyValidRegistryName(java.lang.String code)
          Test if argument is a (non-null) syntactically-valid region/registry code.
private static boolean isValidCcTldFromIPPrefixMapValue(java.lang.String v)
          Routine to validate a putative RHS value for the ccTLDFromIPPrefix table.
static java.lang.String lookupAddrInIPToCcTLDMap(java.net.InetAddress addr, java.util.Map<AddrTools.AddrPrefix,java.lang.String> map, int maxOctetsLookup)
          Do a lookup in the supplied table for the most-specific available location data for the given key; null if none.
 
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
 

Field Detail

BUNDLE_NAME_DEFAULT_GEO_PROXIMITY

private static final java.lang.String BUNDLE_NAME_DEFAULT_GEO_PROXIMITY
The base name of the default geographic proximity bundle. Does not include ".properties" or ".class" suffix, and is assumed to be relative to the root of the package structure.

See Also:
Constant Field Values

BUNDLE_NAME_DEFAULT_CCTLD_FROM_IP_PREFIX

private static final java.lang.String BUNDLE_NAME_DEFAULT_CCTLD_FROM_IP_PREFIX
The base name of the default IP-to-location bundle. Does not include ".properties" or ".class" suffix, and is assumed to be relative to the root of the package structure.

See Also:
Constant Field Values

defaultGeoMap

private static final java.util.Map<GeoUtils.CCTLD,java.util.Set<GeoUtils.CCTLD>> defaultGeoMap
Immutable Map for default proximity from CCTLD to Set of all neighbours. The values (Set<CCTLD>) are also immutable, so they can be returned to callers safely without copying.


DEFAULT_MAX_OCTETS_LOOKUP

private static final int DEFAULT_MAX_OCTETS_LOOKUP
Default maximum prefix octets to look up in registry; strictly positive. This indicates the most specific lookup that we will attempt.

We will try the least-specific lookup first anyway, and just remember the most specific we found, if any, or failing any match an appropriate (short) numeric prefix instead.

This may be overridable from the data.

See Also:
Constant Field Values

ccTLDFromIPPrefix

private static final java.util.SortedMap<AddrTools.AddrPrefix,java.lang.String> ccTLDFromIPPrefix
Cached immutable default ccTLD-from-IP-prefix SortedMap, or empty if none. Loaded at class initialisation.

This may have non-lossy transformations performed on it before it is stored.

The values will have been de-duped (intern()ed) for memory efficiency, since there are relatively few distinct values.

The keys are essentially unique and are NOT intern()ed, since attempting to do so would waste memory and time.


ccTLDFromIPPrefixLongestKey

private static final int ccTLDFromIPPrefixLongestKey
Longest key in octets in ccTLDFromIPPrefix; non-negative. Can be used to restrict search effort at lookup.

Constructor Detail

GeoUtils

private GeoUtils()
Prevent construction of an instance.

Method Detail

getCloseCCTLDs

public static java.util.Set<GeoUtils.CCTLD> getCloseCCTLDs(GeoUtils.CCTLD ccTLD)
Get geographically-close ccTLDs to the specified ccTLD; empty if none, but never null. This logically returns the union of all the groups that the specified ccTLD is present in, from static, built-in data, and any loadable data.

If no near neighbours for the specified ccTLD are known then an empty Set is returned, otherwise the specified ccTLD will be present in the result ie a country is always close to itself.


getCountriesInRegion

public static java.util.Set<GeoUtils.CCTLD> getCountriesInRegion(java.lang.String region)
Get ccTLDs in the specified region; empty if none, but never null. This should be a valid registry name or a name from the "defaultGeoProximity" properties.

The region name should not be a ccTLD nor a numeric partial/full address.

Currently this is computed on the fly each time; we may need to precompute or cache this result.


isSyntaticallyValidRegistryName

public static boolean isSyntaticallyValidRegistryName(java.lang.String code)
Test if argument is a (non-null) syntactically-valid region/registry code. This only checks syntactic validity.

Returns:
true iff three-or-more-ASCII-letter argument (1st upper-case); false for null or otherwise-invalid arguments

isValidCcTldFromIPPrefixMapValue

private static boolean isValidCcTldFromIPPrefixMapValue(java.lang.String v)
Routine to validate a putative RHS value for the ccTLDFromIPPrefix table. A valid RHS (right-hand-side) value is one of:

Returns:
true iff the value is valid on the right-hand-side of an entry in a ccTLDFromIPPrefix map

getCCTLDFromIPPrefix

public static java.util.SortedMap<AddrTools.AddrPrefix,java.lang.String> getCCTLDFromIPPrefix()
Get built-in immutable IPv4-to-ccTLD map; never null.


getCCTLDByAddress

public static GeoUtils.CCTLD getCCTLDByAddress(java.net.InetAddress addr,
                                               boolean quick)
Guess geographical "location" of given IP address (usually of an HTTP client). This attempts to guess the top-level country code corresponding to the likely physical/geographic location of the machine/interface whose IP address is passed.

This may try a number of methods, some of which may require live DNS or other Internet connectivity, but if it fails, will return null. The results are not guaranteed to be accurate.

The code returned, if any, is the lower-case, two-letter, Internet country code, for the region that the IP is in. (This is not the ISO3166-1 code; the United Kingdom is "uk" not "gb".)

(Our implementation here is to get the region, and then return anything that looks like a country-code, else null.)

Parameters:
addr - the (client) address to look up
quick - if true, this will try to minimise time taken and resources used, eg it may avoid going to DNS, so the answer may be less accurate or null more often

getRegionByAddress

public static java.lang.String getRegionByAddress(java.net.InetAddress addr,
                                                  boolean quick)
Guess country or geographic region of IP address; never returns null nor "". This attempts to guess the top-level country code (ccTLD) corresponding to the likely physical/geographic location of the machine/interface whose IP address is passed. (A two-letter lower-case country code.)

Failing that this routine may attempt to return the regional IP registry (eg RIPE or APNIC) that delegates the address, which usually indicates the continent from which the IP address hails. (Starting with an upper-case letter and being more than two characters, ie guaranteed to look like neither a ccTLD nor an IP-address prefix.)

Failing that this will return one or more octets of an IP(v4) address (eg looking like "127" or "127.0" or "127.0.0" or "127.0.0.1") or some leading hex encoding of the network part of an IP(v6) address or a fixed token.

The number of different values that this routine can return is finite, certainly no more than thousands, and all values are human-readable, so this should be directly usable as a key in stats info, for example.

This may try a number of methods, some of which may require live DNS or other Internet connectivity, but if they fail, this will return a numeric value.

The results are not guaranteed to be accurate.

Parameters:
addr - the (client) address to look up; never null
quick - if true, this will try to minimise time taken and resources used, eg it may avoid going to DNS, so the answer may be less accurate or numeric more often
Returns:
non-null, non-empty, short, human-readable, plain-ASCII String

lookupAddrInIPToCcTLDMap

public static java.lang.String lookupAddrInIPToCcTLDMap(java.net.InetAddress addr,
                                                        java.util.Map<AddrTools.AddrPrefix,java.lang.String> map,
                                                        int maxOctetsLookup)
Do a lookup in the supplied table for the most-specific available location data for the given key; null if none. Never uses DNS or other external data.

FIXME: only works at all for IPv4 addresses currently

Parameters:
addr - the address to look up; never null
map - the prefix map; never null
maxOctetsLookup - the maximum number of octets of prefix to look up; non-negative
Returns:
the most-specific value; null if nothing (or a "" value) found

computeProximityByAddress

public static GeoProximity computeProximityByAddress(java.net.InetAddress host1,
                                                     GeoUtils.CCTLD host2CC,
                                                     boolean quick)
Compute approximate proximity of one host to a given country. This is most useful where we know the location of (for example) a mirror host for sure.

Returns "NONE" if it cannot compute a proximity or if the hosts appear to be a long way apart.

Parameters:
host1 - IP address of first host; never null
host2CC - country of second host; never null
quick - if true, do a quick estimate, else be prepared to spend some time and CPU cycles to be as accurate as possible (for example we might have to to reverse DNS lookups)

computeProximity

public static GeoProximity computeProximity(java.lang.String region1,
                                            GeoUtils.CCTLD host2CC)
Compute approximate proximity of a host in a given region to a given country; never null. This is most useful where we know the location of (for example) a mirror host for sure.

Returns "NONE" if it cannot compute a proximity or if the hosts appear to be a long way apart.

Parameters:
region1 - region or country of first host; never null
host2CC - country of second host; never null

DHD Multimedia Gallery V1.60.69

Copyright (c) 1996-2012, Damon Hart-Davis. All rights reserved.