Printing blank lines HttpResponse JDK 11 - java-11

I'm studying the new HttpClient from Java 11 and is not working properly. When I try to print the body from a website the body() method print blank lines:
var httpClient = HttpClient.newHttpClient();
var request = HttpRequest.newBuilder(URI.create("http://iteratorlearning.com")).build();
HttpResponse<String> response = httpClient.send(request,BodyHandlers.ofString());
System.out.println("Printing Body : " + response.body());
Why response.body() doesn't print the content from the body?

If you examine the response status code you will see that it's 301, which is a redirection (moved permanently). By inspecting the response headers you can see that the new location is http://iteratrlearning.com . This is a redirect to a different site, so by default HttpClient will not follow this link (redirect to different sites can often be used for scams).
You can configure the HttpClient to always follow redirect if you want - but I wouldn't recommend it outside of testing purpose, or when you trust the original site (you can use HttpClient::followRedirect(Redirect.ALWAYS))

Related

Helidon Webclient does not seem to work with a proxy

I am facing some trouble with the WebClient when using proxy, i.e. the code below does not work
WebClient webClient = WebClient.builder().baseUri("BASEURL").proxy(getProxy()).build();
Single<WebClientResponse> res = webClient.get().path("/MY/SUB/PATH").addHeader("Authorization", "Bearer " + MY_TOKEN).request();
WebClientResponse webClientRes = res.get();
String resContent = webClientRes.content().as(String.class).get();
public Proxy getProxy(){
return Proxy.builder().type(Proxy.ProxyType.HTTP).host(host).port(port).password("SECRET_PASSWORD".toCharArray()).username(username).build();
}
However the if we use Apache HttpClient the code works (working code below)
HttpHost proxy = new HttpHost(host, port);
CredentialsProvider credentialsProvider = new BasicCredentialsProvider();
credentialsProvider.setCredentials(new AuthScope(proxy), new UsernamePasswordCredentials(username, "SECRET_PASSWORD"));
HttpGet request = new HttpGet("BASEURL" + "/MY/SUB/PATH");
request.setHeader(HttpHeaders.AUTHORIZATION, "Bearer " + MY_TOKEN);
CloseableHttpClient httpClient = HttpClients.custom().setProxy(proxy).setDefaultCredentialsProvider(credentialsProvider).build();
String resContent = EntityUtils.toString(httpClient.execute(request).getEntity());
could anyone let us know if we are overlooking something basic?
We are using helidon MP 2.5.2
When you set a proxy in WebClient, it will use absolute URI in the request because of changes made in https://github.com/helidon-io/helidon/issues/2302 and https://github.com/helidon-io/helidon/issues/3438. The use of absolute URI was implemented because of section 5.1.2 Request-URI in https://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html which states:
The absoluteURI form is REQUIRED when the request is being made to a
proxy.
The problem is that some hosts have issue processing a request with absolute URI as they expect relative URI instead. I have encountered while working on issue https://github.com/helidon-io/helidon/issues/4644 where my testcase has a client that is connecting to KeyCloak as an OIDC server, and KeyCloak will return a 404 because it cannot handle the absoluteURI.
There is a special Webclient config property called relative-uris that you can use to force the request URI to use the relative form rather than absolute. So you can try adding config() in your WebClient.builder() and set that property like this:
.config(Config.create(ConfigSources.create(Map.of("relative-uris", "true")))
where Config needs to be imported as io.helidon.config.Config and ConfigSources as io.helidon.config.ConfigSources. As an alternative, you can also add something like this in your application.yaml:
force-relative-uris:
relative-uris: true
and add config() in the WebClient.builder() like this:
.config(config.get("force-relative-uris"))
where config is instantiated prior to WebClient.builder() like this:
Config config = Config.create();
In the upcoming Helidon v2.5.5 (and v3.0.3), there will be a new relativeUris(boolean relativeUris) in WebClient.builder() so that you don’t have to use config() as in my examples above, which is slightly cumbersome.

NetCore 3.1 PostAsync CustomHeaders not working

I have several RESTful services that working with each other. In one scenario I want to post some data from one service to another service and I want to attach some information in Header of the request. I saw several cases to do this and in the end I came up with this workaround:
var httpClient = new HttpClient();
httpClient.Timeout = TimeSpan.FromMinutes(3);
var httpRequestMessage = new HttpRequestMessage {
Method = HttpMethod.Post,
RequestUri = new Uri(service2Address),
Content = new StringContent(JsonConvert.SerializeObject(obj))
};
httpRequestMessage.Headers.Add("myCustomHeaderKey", "myCustomHeaderValue");
var response = await httpClient.SendAsync(httpRequestMessage);
var responseString = await response.Content.ReadAsStringAsync();
With these lines of code, a Post request sent, but in service2 when I want to get the headers from request, there is no sign of myCustomHeaderKey in headers collection. I inspect Request.Headers in Visual Studio Watch and even try to get custom header with Request.Headers["myCustomHeaderKey"]. So what's wrong here?
EDIT 1
This implementation in based on this tutorial.
I have developed code like yours. Have created Two Asp.net core 3.1 project with standart template. One service is starting localhost:44320 and other localhost:44300
localhost:44320/PostService wrote the your codes.
Then get this url with browser. localhost:44320/weatherforecast/IncomeService function is like below
Finally i put breakpoint to where get request header. Result is like below
There is a not a problem. Maybe you use change request header middleware. Or if you are using something like nginx. this problem maybe nginx configuration.

Is there a way to fire the SOAP request from Selenium and get the response back to any file

In the application which I am automating, below is the requirement.
Need to run the request in the SOAPUI.
This will generate the token response for the provided request.
We will need to use this token in constructing the URL for opening up the application. The token is driven by timestamp. So this will change for every trigger.
Please let me know if there is a way to fire the SOAP request from Selenium and get the response back or to any file.
I simply used Java code for my Soap requests. For editing data in my XML I used the DOM parser. Here is the code I used for this:
#When("^Soap call is made")
public void soap_call_is_made() throws Exception {
XMLHandling xml = new XMLHandling();
String url = "URL here";
String xmlPath = getClass().getResource("location/of/file.xml").getPath();
Document document = xml.getXMLFile(xmlPath);
SOAPMessage soapResponse =xml.makeSoapCall(document, url);
// print SOAP Response
System.out.print("Response SOAP Message:");
soapResponse.writeTo(System.out);
}
The last line will get the token which is in the response.
Edit:
To get specific data from the response, use:
String tagName = "tagnameYouNeed"
String value = xml.getValueByTagName(soapResponse, tagName);
No, Selenium does not handle SOAP/REST request. Instead, you can use java or cURL to handle this situation. Alternatively you can also check rest-assured for this.

How to call API URL windows 8 C#

I am new to windows 8. I want to call api url and the response will be return in terms of json. My Question is how to call below api url in my windows 8 code with c#.
API URL: http://scwin8dashboard.cloudapp.net/shell/~/analytics/reports/reports.ashx?fff=0&report=CampaignCategoriesOverview&languages=&sites=&startDate=20080101&endDate=20121114&addLastModified=true
please help
var uri = "http://scwin8dashboard.cloudapp.net/shell/~/analytics/reports/reports.ashx?fff=0&report=CampaignCategoriesOverview&languages=&sites=&startDate=20080101&endDate=20121114&addLastModified=true";
var client = new HttpClient();
var response = await client.GetStringAsync(uri);
var parser = JsonObject.Parse(response);
For more informations about Http requests see this page.
For JSON related classes see the Windows.Data.Json namespace.

Can't get a token from the Google API

I'm trying to exchange my authorization code for a token with the Google OAuth2 API for my Windows 8 app, but I keep getting HTTP 400 errors.
This is how I perform the request (simplified):
var url = "https://accounts.google.com/o/oauth2/token";
var body = "code=4/LEXF1iAVRZvfCfdQg9r1aFqoYDgV&client_id=904019870963.apps.googleusercontent.com&client_secret=[removed]&redirect_uri=urn:ietf:wg:oauth:2.0:oob&grant_type=authorization_code";
HttpClient httpClient = new HttpClient();
HttpResponseMessage response = await httpClient.PostAsync(new Uri(url), new StringContent(body));
response.EnsureSuccessStatusCode();
Visual Studio usually simply gives me a HTTP 400 bad request error, when I try the same thing in Fiddler I also get an HTTP 400 error, but with this as content:
21
{
"error" : "invalid_request"
}
0
I read all the documentation about Google OAuth, I searched on Google and StackOverflow for this issue, I tried changing all different sorts of things in my code (UrlEncode, etc.), I used the Google API Playground to see what kind of requests it performs and compared it with my own requests (couldn't find a difference except for the return URL, the auth code and the user-agent). No matter what I do, I just can't get this working, I've been stuck for hours already.
Can anyone help me out here?
Read the body content to get the error json you noticed in Fiddler.
HttpClient httpClient = new HttpClient();
var response = httpClient.PostAsync(new Uri(url), new StringContent(body)).Result;
var content = response.Content.ReadAsStringAsync().Result;
content now holds :
{
"error" : "invalid_request"
}
You could project the error in an object, by specifing your error type like: response.Content.ReadAsAsync().Result
For the invalid request part, you should play with UrlEncode. I know you say you tried it, but applying it at the right spots really solves your problem.
var body = "code="+WebUtility.UrlEncode("4/LEXF1iAVRZvfCfdQg9r1aFqoYDgV")+
"&redirect_uri="+WebUtility.UrlEncode("https://yoursite...")+
"&client_id=904019870963.apps.googleusercontent.com" +
"&scope=" +
"&client_secret=********" +
"&grant_type=authorization_code";
HttpClient httpClient = new HttpClient();
var response = httpClient.PostAsync(new Uri(endpoint),
new StringContent(body, Encoding.UTF8, "application/x-www-form-urlencoded")).Result;
This is the code that works for me. Should work for you also.