I have a Perl client which is calling an http restlet service (put method). Some of the parameters in this call contain japanese text. When I printed the contents of these request parameters in the restlet service I found these chars garbled !
This is my PERL client code:
my %request_headers = (
'DocumentName' => $document_name, --> This name is a JAPANESE String
'DocumentDescription' => 'Test Japanese Chars',
'content-length' => 200,
'Content-Type' => 'application/octet-stream; charset=utf-8',
'User-Agent' => "JPCharTester",
);
$s->write_request('PUT', '/test-document/TEST/TEST_DOCUMENT' , %request_headers, $content);
in this call both the values of $context and $document_name are JAPANESE Strings. But ONLY the document_name is received as garbled in my backend service.
Here goes the Service code:
String URL_ENCODING = "UTF-8";
String documentName = requestHeaders.getFirstValue("DocumentName");
System.out.println("Encoded Document Name : "+documentName+" <<<"); --> documentName is garbled here
try {
documentName = URLDecoder.decode(documentName, URL_ENCODING);
System.out.println(>>> Decoded Document Name : "+documentName+" <<<"); --> documentName is garbled here
} catch (java.io.UnsupportedEncodingException ex) {
throwException(ex.getMessage(), Status.SERVER_ERROR_INTERNAL, ex);
}
both the above log statements printed GARBLED TEXT !!
Can someone tell me what is the mistake I am doing and how to fix this ?
Thanks in advance for your help.
Regards,
Satish.
Don't forget to encode the data on the client side as UTF-8. If you say
'Content-Type' => 'application/octet-stream; charset=utf-8'
than that doesn't magically solve the problem. It's just a hint for the receiver in which form it will get the data. You must also send it with the correct format. In perl:
use utf8;
...
'DocumentName' => utf8::encode($document_name),
...
... , utf8::encode($content) ...
Related
I'm trying to gather information from a router (model BGW-210) with BS4 and Python for automation. The Wi-Fi information page requires a device access code which I have available. However, the access code is hashed with a nonce using md5 in the format of: md5('access code' + 'nonce'). The post form looks like this:
payload = {
'nonce': '',
'password': 'access code',
'hashpassword': '',
'Continue': 'Continue'
}
The router also changes each of the letter of the password into '*' for each letter in the field after hashing when I inspected the Payload in the Network tab from my browser.
Here's what I have so far
s = requests.Session()
res = s.get(bgw_210['login_url'], headers=headers)
cookies = dict(res.cookies)
headers['Content-Type']= 'application/x-www-form-urlencoded'
res = s.post(bgw_210['login_url'], headers=headers, cookies=cookies)
html = res.text
soup = BeautifulSoup(html,'html.parser')
# I can get the nonce value from here
print(soup.find('input', {"name":"nonce"}).attrs['value'])
payload = {
'nonce': '',
'password': 'access code',
#'password': '**********',
'hashpassword': '',
'Continue': 'Continue',
}
The nonce would change if I update the payload with the hash password and would no longer be valid. I've tried post requesting with fixed values from the payload that I monitored and input manually via the browser.
I have a Controller that must forward the received request (changing some query parameters) to another server, and returns it's response (with same headers, status and body).
I decided to use HttpClient for doing that.
The problem is that HttpClient converts the content (i.e.: deflating gzip requests), and it breaks the output response.
Here is part of the example:
$response = $client->request($request->getMethod(), $extUrl, [
'headers' => $reqHeaders,
'timeout' => 45,
'verify_host' => false,
'verify_peer' => false,
'body' => $request->getContent(),
]);
#response data
$body = $response->getContent(false);
$statusCode = $response->getStatusCode();
$headers = $response->getHeaders(false);
return new Response($body, $statusCode, $headers);
Considering the second server returns a gzipped content, the response is broken, because it would keep the response header (content-type) but the $body will not be exactly the same, because HttpClient do me the favor of deflate the content.
The question is: is there a way to tell HttpClient to do not touch in my response body?
Or: is there a better way to make this "proxy" controller action?
I found that if accept-encoding is defined in the request headers, it's not inflated by CurlResponse class...
#\Symfony\Component\HttpClient\Response\ResponseTrait::$inflate
$this->inflate = !isset($options['normalized_headers']['accept-encoding']);
And
#\Symfony\Component\HttpClient\Response\response
$response->inflate = \extension_loaded('zlib') && $response->inflate && 'gzip' === ($response->headers['content-encoding'][0] ?? null) ? inflate_init(ZLIB_ENCODING_GZIP) : null;
So, I specified some empty encoding for those cases.
if (empty($request->headers->get('accept-encoding'))) {
//adding some accept-encoding will make httpclient response not to deflate the response (gzdecode) automatically
$request->headers->add(['accept-encoding'=> '']);
}
I still don't know if this is the best approach to forward a request and it's response in the controller, but the above solution solved my problem.
I am trying to start using the computer vision API but I keep getting an empty response. My request in php (as exported by Postman) looks like this:
<?php
$request = new HttpRequest();
$request->setUrl('https://westcentralus.api.cognitive.microsoft.com/vision/v1.0/recognizeText');
$request->setMethod(HTTP_METH_POST);
$request->setQueryData(array(
'language' => 'en',
'handwriting' => 'true'
));
$request->setHeaders(array(
'Postman-Token' => '442d04f7-49a0-4262-9d0f-666fe5240cc7',
'Cache-Control' => 'no-cache',
'Content-Type' => 'application/octet-stream',
'Ocp-Apim-Subscription-Key' => 'KEY'
));
try {
$response = $request->send();
echo $response->getBody();
} catch (HttpException $ex) {
echo $ex;
}
The above code works fine with the ocr endpoint!
The file is passed as binary using Postman.
Edit: I also tried to copy/paste the code from here: https://learn.microsoft.com/en-gb/azure/cognitive-services/computer-vision/quickstarts/php#ocr-php-example-request and if I change the ocr endpoint to recognizeText I get an empty response as well!
Unlike the other Computer Vision endpoints, RecognizeText is an asynchronous operation. Barring some issue with the image, you will get a 202 response instead of the usual 200 response. 202 responses customarily contain an empty response body. In this particular case you can find the URL where you can query for completion of the task. The documentation is here. The header you're looking for is Operation-Location.
I'm trying to access this cookies (the response ones):
When I open the request in the chrome debug tools in the network section I can clearly see that the cookies are present, but how can I access those values from my code? I've never worked with cookies before and I don't know what to do to "extract" them... I'm working on a Ionic2 project using Http.
I've read that the allowCredentials: true header has to be sent but that didn't work...
Here's the request/response details:
Here's the service:
public callLogin(service_guid: string, pos_guid: string, login_data: Object) {
return this.http.post(
this.url + service_guid + "/" + pos_guid + "/ack",
login_data,
{withCredentials: true}
)
.map(response => response.headers);
}
And the caller:
this.__posService.callLogin(login_data.service_guid, login_data.pos_guid, {"password": data.password})
.subscribe(
res => {
console.log("Success:");
console.log(res.get("apsession"); // this returns undefined
},
err => {
console.log("Error:");
}
);
When I try to access the cookie from the header it returns undefined. What am I doing wrong here?
The name of the response header you are trying to get is actually Set-Cookie not apsession. So if you did something like res.get("set-cookie") it would return the first header that matched that name. Since you have more than 1, you could do:
let headers: Headers = res.headers;
headers.getAll('set-cookie');
which returns a list of all headers with that name. You could find apsession in there probably.
See:
https://angular.io/docs/ts/latest/api/http/index/Headers-class.html
https://developer.mozilla.org/en-US/docs/Web/API/Response/headers
https://developer.mozilla.org/en-US/docs/Web/API/Headers
I'm trying to send a subset of messages to Flowdock as output from Logstash. Unfortunately, due to this issue I get essentially nothing back about why my messages aren't making it. Stripping down to a basic example, I see the problem even if I change my output config to the following:
output {
http {
http_method => "post"
url => "https://api.flowdock.com/v1/messages/team_inbox/API_TOKEN"
format => "message"
content_type => "application/json"
message => "{\"source\":\"logstash\",\"from_address\":\"me#example.com\", \"subject\":\"Log Message\", \"content\":\"test\"}"
}
}
I know, though, that output is generally working because if I add the following to output I see log messages written to the file:
file {
path => "/mnt/test.log"
}
I also know that the http message I'm sending to Flowdock should work since
curl -X POST https://api.flowdock.com/v1/messages/team_inbox/API_TOKEN -d "{\"source\":\"logstash\",\"from_address\":\"me#example.com\",\"subject\":\"Log Message\",\"content\":\"test\"}" -H "Content-Type: application/json"
results in a message being posted to the team inbox.
Are there any ways to work around this issue to determine why my output from logstash is failing?
I would start debugging the issue by first sending the requests from Logstash to a service that just outputs the received request, for example RequestBin.
Something like:
output {
http {
http_method => "post"
url => "http://requestb.in/<created_id>"
format => "message"
content_type => "application/json"
message => "{\"source\":\"logstash\",\"from_address\":\"me#example.com\",\"subject\":\"Log Message\", \"content\":\"test\"}"
}
}
After you've made sure that the request Logstash is making is correct, take that request (preferably the exact data) and try to send it to Flowdock using curl or some other means.
At this point you should be able to tell why the request fails in either end and notify the party accordingly (i.e. open a ticket to https://logstash.jira.com/secure/Dashboard.jspa or send an email to support#flowdock.com).