The google drive sdk documentation in "Work with Files and Folders" section says something about the header of a post. Which is:
POST https://www.googleapis.com/drive/v2/files
Authorization: Bearer {ACCESS_TOKEN}
Content-Type: application/json
What does this mean? Does the header really exist on a jsonRequest? Where should this post go to? Should we type the header first, then, put in the json request along with the json string then post it to the server? Or does the ACCESS_TOKEN and the rest of the information be posted along with the URL as a get, like this?
POST https://www.googleapis.com/drive/v2/files?access_token={ACCESS_TOKEN}&etc=whatever&...
I understand that you need to be given an access token or an API key, but where does this go? Does this go on the url string, or does it go inside a post value or jsonRequest?
I've read the jsonRequest in json.org, but still can not get it. Do I need to consider what my content-type, content-length, and content-encoding really means? And if ever I will, where should all of these information go?
Sometimes, the answer is just staring right at my face, and before I know it, I already miss the point. So, can anybody shed me some light?
The Google Drive API is a RESTFul API using HTTP requests as the communication mechanism. The Authorization header is an HTTP header that needs to be sent along the request to authorize it. JSON is only used as the resource representation.
However, the Drive API also supports passing the OAuth 2.0 access token as a ?access_token= query parameter which can be more convenient for you.
If you are using one of supported client libraries, all this is taken care of for you through class abstractions.
The header is a standard part of an HTTP request. The standards of an http request are header fields and request methods.
POST https://www.googleapis.com/drive/v2/files
Request methods on this example is a POST and it sends the data to google drive api server. This means, the Google Drive API will accept POST requests.
Authorization: Bearer {ACCESS_TOKEN}
The Authorization, in this case, is an ACCESS_TOKEN which is the API_KEY. The server may receive also a GET request. The server checks to see if the user is authorized before it does its process: create, delete, update, or get files (depending on what the Http Request json data sends).
Content-Type: application/json
The Content-Type tells the server that the Mime Type of the HTTP request that will be sent is a json string. The Mime Type may be already a standard for the server, which means that you don’t even have to put it anywhere in your code because it assumes that you will be sending a json string, and it will receive it once you do POST. Otherwise, it will give an error. Content-Type field will always receive the Mime Type. (For a list of Mime Types, you may refer to http://en.wikipedia.org/wiki/MIME_type.)
Since HTTP Header is a standard, you will need to know what type of standards there are that Google Drive API server uses. Then, follow wherever the header fields are placed. For example, the ACCESS_TOKEN is located in the url string as a GET, and json string is located in a POST. (For a list of HTTP Header, you can also get a reference from http://en.wikipedia.org/wiki/List_of_HTTP_header_fields.)
Related
I have a problem with handling POST requests in Google Apps Script. I've created simple project with following functions:
function doGet(e){
return ContentService.createTextOutput("test").setMimeType(ContentService.MimeType.TEXT);
}
function doPost(e){
return ContentService.createTextOutput("test").setMimeType(ContentService.MimeType.TEXT);
}
When I try to send a GET request from postman I get correct response - as expected. However when I try to send POST request I get 405 Method not allowed and HTML error page in response. In deployment settings I set that it should execute as me and should be accessible to everyone.
What am I missing? How to make POST requests work with Google Apps Script?
EDIT:
So as Heiko Theißen wrote below there is 302 redirect at first.
As I can see Postman follows that redirect and sends POST once again to new URL but this request fails and I still don't know why unfortunately. I can see in security section that there is header Allow: HEAD, GET.
I cannot see any preflight request from Postman (as TheMaster suggested).
About reproducibility: I've pasted complete content of google apps script, and I mentioned that I am making request from postman. Here is link to current deployment of that script: https://script.google.com/macros/s/AKfycbyHdVpclM7pH1BB3IzwNjtcH07DF75H8ldqeLQCwQnX71lMs371g-UO-i8JaI5_zRqrDw/exec
Also here is screenshot from Postman - I'm just sending empty POST request without any custom headers. Tried also sending plain text or json as payload but results were the same each time.
So back to my original question: How can I receive POST request successfully in google apps script deployed as Web App?
I make it workable from postman by disabling the annotated option from settings.
If the preflight explanation given by TheMaster does not solve your problem, the following might help:
Requests to Google Apps Script always happen in two stages: The first request draws a redirection response to a generated URL, and the second request to that URL draws the response that you programmed (the text output "test").
When the first request is a POST request, the redirection response has status "302 Found", and the specification is ambiguous about what method the second request should have:
Note: For historical reasons, a user agent MAY change the request
method from POST to GET for the subsequent request. If this
behavior is undesired, the 307 (Temporary Redirect) status code
can be used instead.
Google Chrome makes the second request as a GET request (without repeating the POST payload, which the server already knows under the generated URL) and this works.
However, if your browser or Postman client does not change the method and makes the second request again as a POST (and your screenshot shows this is true), the server does not accept this and responds with "405 Method Not Allowed".
In other words: Google Apps Script expects the second request to be a GET request, but not all clients behave like that, because the specification is ambiguous at this point. Workarounds:
You can influence the behavior of Postman so that it does not preserve the POST method between the first and second request. See here.
Google Apps Script could avoid the ambiguity by responding to the first request with "303 See Other", but it does not. Perhaps create an issue for that?
All the incoming request to api management will have a token in a header, before backend service is hit token has to be verified. To verify token a GET tokenVallidationApi is to be hit and the response will tell us whether the token is valid or not. If the response exists for token validation , we have to take out few entries from response and enrich the body/header to hit the backend api. I am very new to api management tool and just figuring out how can we achieve this with azure api management?
This is possible. You would have to implement your policies like something below
1. Validate Token
For this, you would first call the validation endpoint using send-request. You could also implement caching using value caching policies for multiple requests.
The doc also highlights how you can extract value from the response body.
2. Transform Body & Headers
For headers, you would use the set-header policy and for the body, you would use the set-body policy.
I'm trying to use the reddit api in a practice app to practice parsing JSON in Swift, and I've registered to get an access token, but now I'm confused as to where to put it. In other APIs I've used, I'd just put the access token string (?) somewhere in the endpoint url and that would be it, but I can't see anything pertaining to that in the documentation. For example if I'm trying to access https://api.reddit.com/api/v1/top/, where would I add my access token?
In the OAuth documentation is says to use the url https://www.reddit.com/api/v1/authorize?client_id=CLIENT_ID&response_type=TYPE&
state=RANDOM_STRING&redirect_uri=URI&duration=DURATION&scope=SCOPE_STRING but that seems to need:
CLIENT_ID
RANDOM_STRING
URI
DURATION
SCOPE_STRING
I plugged in all the necessary values according to the documentation, and it redirected me to the front page of reddit (I gave https://www.reddit.com/ as my redirect uri)
In previous practice apps with other APIs, I would simply have a single url (that included my auth token) and I'd plug that url into my function that parses the data. Now that I've followed the OAuth directions, I still can't seem to find an endpoint url that I can use in my app.
I tried https://api.reddit.com/api/v1/top in my browser and it says {"message": "Unauthorized", "error": 401}, and I tried https://www.reddit.com/api/v1/myAccessToken where myAccessToken is the string they gave me when I registered. This leads me to a "page not found" on Reddit.
What do I need to do here to get a basic endpoint url that gives me the JSON data for, just for example, recent posts?
I'm having trouble getting my stateless authorization to work.
I currently have my server adding the Authorization header with the generated JWT to the HTTPResponse for the client.
My problem is the Client-side of things. I'm not quite understanding how to get the header I added on the HTTP-Response to send back in all HTTP-Requests. I've been trying to use the Bearer schema and tried without any schema but nothing seems to be working. I am not using OAuth so I'm not sure if the Bearer schema works without it. I've also tried Basic and Digest.
This is how it looks when I send it from the server.
Authorization: Bearer s5la8kdj4flak2.l4as5kdjfow2ie.owekj6nvowe4i3ej
My question is really, how do I send this Authorization header back to the server to be authenticated?
Any help would be much appreciated.
There is no way to send an Authentication header back and forth the way I was asking above. You would have to be explicitly be using Basic Authorization, which I was not.
The way I ended up doing it was making a cookie named Authorization where the body had the JWT. Cookies are automatically sent back to the server in the HTTPRequest, where I was able to strip it out in a custom filter.
Put JWT into cookie, this will protect it against theft by XSS attack
I'm using a token style authentication process. After the client has obtained a token, it is either set in the client's cookies (for Web) or the authorization headers of the client's requests (for mobile). However, in order to obtain a valid token, the client must first "log in" using an valid username/password combination. My question is this:
Is there any added security by sending the username/password combination in the authorization header vs. as parameters in the JSON body of the request (assuming I'm using HTTPS)?
I only need to send the username/password combination "once" per session in order to obtain the token. Do I gain anything by doing it a la "basic-auth" style?
There's no added security in sending credentials in the Authorization header vs. a JSON body. The advantage in using the Authorization header is that you leverage on the standardized HTTP semantics, and you don't have to document exactly what clients should do. You can simply point them to the RFCs.
If you're concerned about being really RESTful, I'd say using the Authorization header instead of rolling your own method is a must.