I have 3 pieces of information that form a url/uri.
String myscheme = "https";
String basePath = "www.theothercompany.com";
String suffixPath = "/api/v1/things";
How do I "compose" a full URI or URL with (only) the three things above.
I've been through several constructors for : https://docs.oracle.com/javase/8/docs/api/java/net/URI.html and https://docs.oracle.com/javase/8/docs/api/java/net/URL.html
like I tried this:
URI x = new URI(myscheme , basePath , suffixPath);
or
URI y = new URI(myscheme , basePath , suffixPath, "");
But I keep getting things like
httpswww.theothercompany.comapi/v1/things
obviously, removing "parts" like "://" and "/".
I don't have a port, or a ssp or a user or textfile...or other things I saw in the constructors of the 2 above oracle links.
I can't believe this is roadblocking me !!
Below are some other (already) pulled in packages. I do not want to add another one (like org.apache.http.client.utils.URIBuilder for example).....to bloat the dependencies.
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.reactive.function.client.WebClient;
and
compile group: 'org.springframework.boot', name: 'spring-boot-starter-webflux', version: springBootVersion
compile group: 'org.apache.commons', name: 'commons-lang3', version: commonsLangVersion
compile 'org.projectreactor:reactor-spring:1.0.1.RELEASE'
APPEND
Ok, as per suggested, I fixed my mislabelling of the 3 parts.
String myScheme = "https";
String myHost = "www.theothercompany.com";
String myPath = "/api/v1/things";
java.net.URL computedFullUrl = null;
String urlToStringValue = "";
String urlToExternalFormValue = "";
String urlToUriStringValue = "";
try {
/* this works....or does not exception out */
computedFullUrl = new java.net.URL(myScheme, myHost, myPath);
if (null != computedFullUrl) {
urlToStringValue = computedFullUrl.toString();
urlToExternalFormValue = computedFullUrl.toExternalForm();
urlToUriStringValue = computedFullUrl.toURI().toString();
}
} catch (Exception ex) {
//throw new RuntimeException((ex));
// temporary swallow
String temp = ex.getMessage();
ex.printStackTrace();
}
So the above works.
I get (all three "convert back to a full string" values of) :
https://www.theothercompany.com/api/v1/things
I finally figured it out.
It had nothing to do with URI or URL.
When i read the values from a property file, the beginning "/" was being stripped from "/api/v1/things"
The value in the string was "api/v1/things". (no quotes of course). That was my issue.
I'll leave the question up so others can learn from my faux pas.
Gaaaaaa.
The problem is partially caused by not using the correct technical terms:
www.theothercompany.com
is a host name, not a “basePath”./api/v1/things
is the path, not a “suffixPath”Obviously, you want to construct a hierarchical URI, but one of the constructors you use, is designed to construct an opaque URI¹, expecting the arguments scheme
, ssp
(scheme specific part), and fragment
.
The constructor’s documentation precisely describes the outcome:
This constructor first builds a URI in string form using the given components as follows:
- Initially, the result string is empty.
- If a scheme is given then it is appended to the result, followed by a colon character (
':'
).- If a scheme-specific part is given then it is appended. Any character that is not a legal URI character is quoted.
- Finally, if a fragment is given then a hash character (
'#'
) is appended to the string, followed by the fragment. Any character that is not a legal URI character is quoted.
leading to https:www.theothercompany.com#/api/v1/things
.
Since you want to construct a hierarchical URI composed of scheme
, host
, and path
, the second constructor is the right one:
public URI(String scheme, String host, String path, String fragment)
Constructs a hierarchical URI from the given components.
So using new URI(myscheme , basePath , suffixPath, "")
leads to https://www.theothercompany.com/api/v1/things#
.
When you change it to new URI(myscheme , basePath , suffixPath, null)
, you’ll get https://www.theothercompany.com/api/v1/things
.
This demonstrates why named factories are preferable over overloaded constructors, as such a semantic difference between two constructors only differing by one parameter, is not very intuitive.
¹ or to construct a hierarchical URI by specifying the syntactical elements manually, which is rarely needed