Google Cloud Vision API 'Request Admission Denied' - ocr

I am new to Google Cloud Vision API. I am doing OCR on images primarily for bills and receipts.
For a few images it is working fine, but when I try some other images it gives me this error:
Error: { [Error: Request Admission Denied.]
code: 400,
errors:
[ { message: 'Request Admission Denied.',
domain: 'global',
reason: 'badRequest' } ] }
This is my code:
// construct parameters
const req = new vision.Request({
image: new vision.Image('./uploads/reciept.png'),
features: [
new vision.Feature('TEXT_DETECTION', 1)
]
})
vision.annotate(req).then((res) => {
// handling response
//console.log(res.responses[0].textAnnotations);
var desc=res.responses[0].textAnnotations;
var descarr=[];
for (i = 0; i < desc.length; i++) {
descarr.push(desc[i].description);
}

Ran into this problem as well. It was an image size issue. I don't know what the hard limit is. 4MB worked, but 9MB didn't, it's somewhere in between there.

I was able to work around this by saving the image as another format and submitting that instead; there was something "wrong" (or at least, unexpected by Google) with the image file itself. Not sure about image manipulation in the language you're using (js?), but in Python it was as simple as:
from PIL import Image
bad_image = Image.open(open('failure.jpg', 'rb'))
bad_image.save(open('success.png', 'wb'))

The Best Practices doc says that the image file size should not exceed 4 MB. Based on this responses above, this could be the problem.

Interesting. I ran into the same problem today, using Google's Java client. The way I read James' answer, he had a JPEG file that failed, but worked as a PNG file. In my case, I had a PNG file that failed, but worked as a JPEG.
I had concluded it was a size limitation, as I'd expect JPEGs to be typically smaller than PNGs; however, James' experience suggests otherwise.
I couldn't find any relevant documentation in Google's Javadocs. Since the response is a 400 error, perhaps the Java library is not encoding the image buffer correctly.

Related

Postman interceptor request running forever

I am trying to intercept a website - https://www.kroger.com/pl/chicken/05002. In the chrome network tab, I see the request as below, with the details of the products nicely listed as JSON
I copied the cURL as bash and imported it as raw text in Postman. It ran forever without any response. Then I used the intercept feature and still it is running forever.
When both the requests are exactly same, why is it running in Chrome and not in Postman? What am i missing? Any help is appreciated, thanks in advance.
This is probably happening because they don't want you to do what you are trying to do. Note the "filter.verified" param in the URL.
You may want to try reaching out to them for an external API token - especially if you are creating an app or extension to compare competitive prices with the intention of distributing said app or extension - regardless of if it is for financial compensation or not.
Ethically questionable workaround (which would defintely need to be improved upon - this is simply an example of how you could solve your problem...):
GET https://www.kroger.com/search?query=chicken&searchType=default_search&fulfillment=all
const html = cheerio(responseBody);
var results = [];
html.find('div[class="AutoGrid-cell min-w-0"] > div').each(function (i, e)
{
results.push({
"Item": e.children[e.children.length-3].children[0].children[0].children[0]["data"],
"Price": e.children[e.children.length-4].children[0].attribs["value"]
})
});
console.log(results);
If you are unable to obtain an API token from them, this would probably be a legal way to accomplish what you want.

JSZip read downloaded data (Angular 2)

I am trying to use JSZip to unzip a JSON file but due to my lack of understanding how JSZip works I get the response in a format that I do not know how to use.
So far this is my code:
this.rest.getFile(this.stlLocation).subscribe(
data => {
let JSONFIle = new JSZIP();
JSONFIle.file(data.url, data._body, {binary : true, compression : 'DEFLATE'});
console.log(JSONFIle);
},
err => {
this.msgs.push({severity: 'error', summary: 'Error Message', detail: err});
}
);
So I download a file using an angular 2 service and I use an observable to get the response. When the data is received I finally call JSZip and try to unzip the file but the result of the operation is an intricate object with my data scattered all over the place and buried inside several layers. All I want is the unzipped JSON file that I can open and process.
Thank you for your help,
Dino
after a bit of reading I have realized I was going on the wrong path. If you are downloading the file to a browser, you shouldn't have to do anything. Browsers add the Accept-Encoding: 'deflate' header automatically; it is both unnecessary and not good practice to do this at a DOM/JS level. If you are using NGINX the following link may help you out:
NGINX COMPRESSION AND DECOMPRESSION

Program-generated KML file validates, but doesn't work

I had a co-worker that normally worked with Google Maps and now I am creating my first map. I am using what they developed in the past and making the changes for what I need. They created a script that sets some of the map defaults, so that is why things might look slightly different.
var map = new Map();
map.loadMap();
var kml = new google.maps.KmlLayer({ url: 'http://api.mankatomn.gov/api/engineeringprojectskml', suppressInfoWindows: true });
kml.setMap(map.map);
The map loads. My KML file doesn't load. I don't get any errors in the console. When I replace the url with a different URL http://www.mankato-mn.gov/Maps/StreetConstruction/streetconstruction.ashx?id=122 it'll work just fine. My new feed does validate. Is there a issue with my web service?
Update: After a few days, I am still having the issue. So I am pretty sure this isn't a DNS issue anymore. I created a jsFiddle to see if it is my code or something else. I started with Google's sample code and changed the URL of the KML file to both my web service and to a static version of the generated file. Both are valid KML files. Neither work. If there was a syntax error, wouldn't the API report that?
You can get the status of a KML layer with
kml.getStatus();
which in this case return:
"INVALID_DOCUMENT"
Now, if I request your URL from the browser, I get
<Error>
<Message>An error has occurred.</Message>
</Error>
So it seems if there ever was a valid KML there, it isn't anymore. Assuming from your question I can oly guess it was above weight limit, or you weren't associating it with a valid instance of map.
For getStatus to return something useful, you must wait for Google Maps API to try and load the KML layer you declared. For example, you can add a listener on the status_changed event.
var kmloptions={
url: 'https://dl.dropboxusercontent.com/u/2732434/engineeringprojectskml.kml',
suppressInfoWindows: true
};
var newKml = new google.maps.KmlLayer(kmloptions);
newKml.setMap(map);
google.maps.event.addListenerOnce(newKml, 'status_changed', function () {
console.log('KML status is', newKml.getStatus());
});
in this case (note that I'm using the alternative URL you used in the jsFiddle), I still get INVALID DOCUMENT.
Update: it seems the problem was the encoding of the file (UTF-16 BE is meant to be binary). I converted it to utf-8 and reindented (it's in my public dropbox now)
You can check if the DNS is setup by:
Going to the url in your browser. Do this with cache emptied and history ereased (private mode is best). If it ends up at your server and the right file it is not a DNS problem.
Move the file to a location you're sure it is reachable without any DNS issues. e.g. http://www.mankato-mn.gov/Maps/StreetConstruction/engineeringprojectskml
If the problem persists make sure that your KML syntax and Javascript is 100% correct. Also check out https://developers.google.com/maps/documentation/javascript/examples/layer-kml if you're still having any issues.

How to set description in the BoxFileUpload request?

I am using the Box windows V2 SDK to upload files to my Box account using the following code:
BoxFileRequest request = new BoxFileRequest()
{
Parent = new BoxRequestEntity() { Id = "0" },
Name = attachment.Name,
Description = "This is failing to be sent..."
};
client.FilesManager.UploadAsync(request, new MemoryStream(attachment.FileContent)).Result;
Uploading the file works great. However, I can not get the description field sent to the box server. Is it possible to upload a file with a description, or do I have to call FilesManager.UpdateInformationAsync after the file has been uploaded to accomplish this? It would be nice if this was an option so I could reduce the number of API calls..
The description must be set in a separate API request after uploading the file.
We have heard reusing some of the request objects may cause some confusion on what can be done with each request. We are evaluating whether or not this should be changed

Handling IE and that it doesn't handle fileSize, etc

I'm using v3.9 UI with jQuery wrapper:
Now that I've solved my 'Maximum Request Length Exceeded' error within IE9 (from here:
FineUploader Error Handling
). All my FineUploader code is within this other link, and didn't think I needed to post it again.
I'm now looking for a better way to let IE users know when they've attempted to upload a file that's too large (Chrome, FF users get the too large file alert, so this isn't a problem). I don't think I need to mess with the 'messages' option as these are working as they should for all the other browsers. It's IE that's not working as it should! IE users will get all the way up to the server with the file they've selected. For handling uploading a file that exceeds the fileSize property, I have code on my server side to checks content length > 'n' and if so then return JSON success = false. See below:
[HttpPost]
public JsonResult UploadFile(HttpPostedFileWrapper qqfile, int surveyInstanceId, int surveyItemResultId, int itemId, int loopingIndex)
{
bool isValid = false;
// file is too big, throw error.
if (qqfile.ContentLength > (1024*1024*2.5))
{
return CreateJsonResult(false);
}
More Code here if the file is 'good'
}
private JsonResult CreateJsonResult(bool isSuccess)
{
var json = new JsonResult();
json.ContentType = "text/plain";
json.Data = new { success = isSuccess };
return json;
}
This short circuits an invalid file upload based on size. Great, but can I return more than just success=false and have this additional JSON value used by FineUploader to display a more useful message to the user? Currently all that shows is 'Upload Failed'. How do I reference the specific html element for that invalid file, so I can add a more descriptive error?
Also, I do have the .on('error') method, but I'm not sure how to trigger this. This would be a logic place to look, as the file upload size issue IS an error. Help? Thanks.
Using the Content-Length of the request to enforce file size restrictions is not a good idea. All upload requests sent by Fine Uploader, by default, are multipart encoded. The Content-Length for multipart encoded requests is the size of the ENTIRE request, not just the file.
In a comment to your answer for your last question, I pointed to a specific section of the documentation that allows you to control the failure text that appears next to a file in Fine Uploader UI mode. All you have to do is set the mode property of the failedUploadTextDisplay option to "custom". Server-side, return the error message text you would like to appear next to the failed file in an "error" property of your JSON response. See the bottom of the "handling errors" documentation section for more details.
UPDATE
It looks like you are using the ContentLength property of the HttpPostedFileWrapper which returns the size of the uploaded file. This was a bit confusing for me at first, since Content Length generally refers to the size of a request. The name choice for this property was a poor one on Microsoft's part, IMHO. So, you can disregard #1 in my answer.