Class CalendarAddressGuard
Why. A subscription makes the server fetch a URL a user typed, again and again. Unguarded, that turns eXo into a client of whatever sits on its own network — an administration console on loopback, a database's HTTP port on a private address, the cloud metadata endpoint handing out credentials.
What it decides. The URL's shape — http or https (webcal:// is
read as https), no credentials in it, a port in the allowed set — and the
addresses its host resolves to: loopback, link-local (the metadata address
169.254.169.254 among them), private, carrier-grade NAT, multicast,
broadcast and reserved, unspecified, IPv6 unique-local and site-local, and
each of those spelled as an IPv4 address inside an IPv6 one (mapped,
compatible, NAT64, 6to4) are refused unless the deployment allows internal
addresses. The rules are caldav-integration's
CaldavServerUrlValidator#isBlocked, copied rather than depended on —
caldav-integration depends on agenda — and extended with the reserved
range, 198.18.0.0/15 and the NAT64 and 6to4 forms.
Where the address is checked. resolveAllowed(java.lang.String) is the resolver
of the HTTP client's connection manager, so it judges the very addresses the
client then connects to, for every connection it opens — every redirect hop
included. A name that resolved to a public address when the user typed it and
to a private one when the job refreshes it (DNS rebinding) is refused at that
connection, not trusted from an earlier answer. What stays outside its reach:
a public server that itself relays the request inward, and the time a refused
or unreachable answer takes, which says something about a public host.
-
Nested Class Summary
Nested ClassesModifier and TypeClassDescriptionstatic interfaceResolves a host name to its addresses; the JDK's by default.static final classThrown byresolveAllowed(java.lang.String)for a host resolving to an address the platform must not reach. -
Field Summary
Fields -
Constructor Summary
ConstructorsConstructorDescriptionCalendarAddressGuard(boolean allowInternalAddresses, Set<Integer> allowedPorts) The guard of a deployment. -
Method Summary
Modifier and TypeMethodDescriptioncheckTarget(URI uri) Checks the shape of a URL about to be read — the one typed, or the target of a redirect: absolute, http or https, no credentials, a host, a port in the allowed set.static booleanisBlocked(InetAddress address) Whether one address is outside what a calendar link may point at.Reads a URL as the user typed it: trimmed,webcal://andwebcals://read ashttps://, the fragment dropped, then checked bycheckTarget(java.net.URI).resolveAllowed(String host) Resolves a host and refuses it when ANY of its addresses is one the platform must not reach — a name answering one public and one loopback address is a name reaching loopback.
-
Field Details
-
MAX_URL_LENGTH
public static final int MAX_URL_LENGTHLongest URL accepted.- See Also:
-
-
Constructor Details
-
CalendarAddressGuard
The guard of a deployment.- Parameters:
allowInternalAddresses- whether internal addresses may be read at allallowedPorts- the ports a URL may reach, implicit default ports included
-
-
Method Details
-
normalize
Reads a URL as the user typed it: trimmed,webcal://andwebcals://read ashttps://, the fragment dropped, then checked bycheckTarget(java.net.URI). Nothing is resolved here.- Parameters:
url- the URL as typed- Returns:
- the URL to read
- Throws:
CalendarFeedException- with the reason it is refused
-
checkTarget
Checks the shape of a URL about to be read — the one typed, or the target of a redirect: absolute, http or https, no credentials, a host, a port in the allowed set.- Parameters:
uri- the URL- Returns:
- the URL with its scheme lower-cased
- Throws:
CalendarFeedException- with the reason it is refused
-
resolveAllowed
Resolves a host and refuses it when ANY of its addresses is one the platform must not reach — a name answering one public and one loopback address is a name reaching loopback. This is the HTTP client's resolver: its answer is what the client connects to.- Parameters:
host- the host, brackets of an IPv6 literal allowed- Returns:
- the addresses, every one allowed
- Throws:
CalendarAddressGuard.RefusedAddressException- when an address is refusedUnknownHostException- when the host resolves to nothing
-
isBlocked
Whether one address is outside what a calendar link may point at.The JDK predicates cover the any-local, loopback, link-local, site-local (RFC 1918 in IPv4, fec0::/10 in IPv6) and multicast addresses; the byte inspection covers the rest, and the IPv4 address an IPv6 address may carry, which is how
::ffff:127.0.0.1or64:ff9b::a9fe:a9fewould otherwise walk past a loopback or metadata check.- Parameters:
address- one resolved address- Returns:
- true when the platform must not reach it
-