How to properly set Authorization to consume Wordpress Rest API (Oauth1) with Nativescript[2.5.4]? - nativescript

I'm trying to consume the WP Rest API with Nativescript.
The WP API and the Authorization with OAUTH1 is already well setup and tested with POSTMAN.
Nativescript Login function to consume rest is already setup too and work without OAUTH.
Now I'm trying to Login with OAUTH here the code :
authorizationString = 'OAuth oauth_consumer_key="T2yXcbN28Ufj",
oauth_token="AmEVr5oSNmbKyZKccFjtmnSk",
oauth_signature_method="HMAC-SHA1",
oauth_timestamp="1492267438",
oauth_nonce="rGFJG2",
oauth_version="1.0",
oauth_signature="Ru%2BaSvsZn2liesd2ENy8GeNsdHY%3D"';
login(user: User){
console.log("Try to login User : " + user.email);
let headers = new Headers({"Authorization": authorizationString});
let body = JSON.stringify({
username: user.username,
email: user.email,
password: user.password
});
headers.append("Content-Type", this.contentType);
return this.http.post(
this.api,
body,
{headers: headers}
)
.map( response => response.json() )
.do(data => {
//Do work!!
})
.catch(this.handleErrors);
}
But i got an error, this error means the autorization is not well formatted or sent :
"data": {
"code": "rest_cannot_access",
"message": "Only authenticated users can access the REST API.",
"data": {
"status": 401
}
}
How to properly use oauth1 with Nativescript?

I just switched to OAUTH2 by using a opensource plugin :
https://github.com/wlcdesigns/WP-OAuth2-Server-Client
and it's more easy to use with the authorization : Bearer

Related

Axios JWT doesn't send

I have a project divided in two layers. The back-end is developed in spring boot, secured by Sprint security and JWT, and the front-end is developed in Vue.js, using Axios library for communication between layers.
I receive the "Bearer token" authentication properly, and all the authentication process is done correctly. The issue appears when I try to send a request with a token header to access content but the token doesn't send, and the Spring boot returns null without the content.
Here is the code
getOffers: function () {
if (localStorage.getItem("userSession")) {
this.aux = JSON.parse(localStorage.getItem("userSession"));
this.token = this.aux.token;
this.tokenHeader = "Bearer "+this.token;
alert(this.tokenHeader)
};
console.log(`Bearer ${this.token}`)
axios.
get('http://localhost:8080/api/v1/offer', {'Authorization' : `Bearer ${this.token}`})
.then(response => {
console.log(response);
this.offers = response.data
}).catch(e => console.log(e))
}
P.S: When I make a request in Postman, it works fine and returns the desired object. Here is a postman example:
postman
Correct way to pass header is :
axios.get(uri, { headers: { "header1": "value1", "header2": "value2" } })
In your case try this:
axios.get('http://localhost:8080/api/v1/offer', { headers:{Authorization : `Bearer ${this.token}`} })
Also, check in console if this gives correct Bearer token:
console.log(`Bearer ${this.token}`)
Register the Bearer Token as a common header with Axios so that all outgoing HTTP requests automatically have it attached.
window.axios = require('axios')
let bearer = window.localStorage['auth_token']
if (bearer) {`enter code here`
window.axios.defaults.headers.common['Authorization'] = 'Bearer ' + bearer
}
And no need to send bearer token on every request.

Google Smart home report state error 403

I'm reporting states for devices using http post with a jwt generated using service account. Below is the payload for jwt
{
"iss": "<service-account-email>",
"scope": "https://www.googleapis.com/auth/homegraph",
"aud": "https://accounts.google.com/o/oauth2/token",
"iat": <current-time>,
"exp": <current-time-plus-one-hour>
}
after this I sign the jwt using the private key for my service account using the python library google.auth.crypt.RSASigner.from_service_account_file(path)
and generate the jwt token. I am further using this token to obtain the access token from https://accounts.google.com/o/oauth/token, which is also successful.
After obtaining the access token I am making a post request to
https://homegraph.googleapis.com/v1/devices:reportStateAndNotification?key=api_key
with headers
{"Authorization": "Bearer <token>", "X-GFE-SSL": "yes", "Content-Type": "application/json"}
and json data
{ "requestId": "ff36a3cc-ec34-11e6-b1a0-64510650abcf", "agent_user_id": "1234", "payload": { "devices": { "states": { "1458765": { "on": true }, "4578964": { "on": true, "isLocked": true } } } } }
But this gives me
{'error': {'code': 403, 'message': 'The request is missing a valid API key.', 'status': 'PERMISSION_DENIED'}}
I followed the steps from
https://developers.google.com/actions/smarthome/report-state
is there anything i'm doing wrong? or am I missing any steps?
UPDATE:
I added the api key to the uri now it gives me another error in response
{'error': {'code': 403, 'message': 'The caller does not have permission', 'status': 'PERMISSION_DENIED'}}
how do I resolve this issue?
In order to report the state to the Home Graph you have to:
Create a Service Account for the token creation from your SmartHomeApp project:
Go to APIs & Services => Click on Credentials
Click on Create credentials => Click on Service account key
Fill with your data creating a new New service account => Select the role Service Accounts > Service Account Token Creator
Download the JSON file with your keys and certificate
Get a valid signed JWT token:
credentials = service_account.Credentials.from_service_account_file(service_account_file, scopes="https://www.googleapis.com/auth/homegraph")
now = int(time.time())
expires = now + 3600 # One hour in seconds
payload = {
'iat': now,
'exp': expires,
'aud': "https://accounts.google.com/o/oauth2/token",
'scope': SCOPE,
'iss': credentials.service_account_email
}
signed_jwt = google.auth.jwt.encode(credentials.signer, payload)
Obtain a valid Access token:
headers = {"Authorization": "Bearer {}".format(signed_jwt.decode("utf-8")), "Content-Type": "application/x-www-form-urlencoded"}
data = {"grant_type": "urn:ietf:params:oauth:grant-type:jwt-bearer", "assertion": signed_jwt}
access_token = requests.post("https://accounts.google.com/o/oauth2/token", data=data, headers=headers).get("access_token")
Send the reported states:
headers = {"Authorization": "Bearer {}".format(access_token), "X-GFE-SSL": "yes"}
data = {"requestId": request_id, "agent_user_id": agent_user_id, "payload": {"devices": {"states": states}}}
requests.post("https://homegraph.googleapis.com/v1/devices:reportStateAndNotification", data=json.dumps(data), headers=headers)
NOTE: in order to work these snippets require to import google.auth.jwt, from google.oauth2 import service_accountand import requests from google-auth, google-auth-httplib2 and requests packages.

Directory API returns 403 forbidden

i'm trying to use the directory API by using a service account that I've enabled his Domain-wide Delegation and off course also authorized this service from the admin console using the json file credetials downloaded when creating the service account.
I've also enabled the admin sdk from the google developers console
and i'm using the googleapi library
in order to get access token for the service account
import * as google from 'googleapis';//google sdk for api+Oauth
//creating JWT auth client for service account:
const jwtClient = new google.auth.JWT(
client_email,
null,
private_key,
scope, // (included the "https://www.googleapis.com/auth/admin.directory.user" scope)
null,
);
let tokens
jwtClient.authorize( (err, tokens)=> {
if (err) {
console.log(err);
return;
} else {
tokens = tokens
}
// Make an authorized request to list of domain users.
let url = `https://www.googleapis.com/admin/directory/v1/users?domain=mydomain`;
let headers = {
"Content-Type": "application/json",
"Authorization": `Bearer ${tokens.access_token}`
}
request.get({
url: url,
json: true,
headers: headers,
}, (err, res, body: {}) => {
this.handleResponse(err, res, body, resolve, reject);
});
});
})
}
the tokens are retrived succefully but when sending the users list request i'm receiving 403 "Not Authorized to access this resource/api"
on the other hand when using the google explorer api with the same params it work's
Looks like you didn't provide a subject when constructing the JWT object (in the line after scope, in your code). You should provide the email address of an admin there, so that you get a token impersonating that admin. Otherwise, you're acting as the service account itself, that doesn't have access to your domain's directory (and can never have access - that's why you must impersonate an admin).

How to add Authorization header in vueJs

I'm trying to send a post request from a vuejs app to a spring backend with which I'm attaching a jwt authorization header.
I have tried with vue-resource
Vue.http.headers.common['Authorization'] = 'Bearer YXBpOnBhc3N3b3Jk';
and the backend headers are like this
{accept-language=en-US,en;q=0.5, origin=http://localhost:8080, host=127.0.0.1:8084, access-control-request-headers=authorization, connection=keep-alive,...
But if i use postman to send the same request, the backend headers are like this
{authorization=Bearer eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiI1OTBhYWFmMjRhNjQ3ZjRiYmZlMDBhMDQiLCJzdWIiOiJiYmIiLCJpYXQiOjE0OTM5NzUxMDQsInJvbGVzIjoidXNlciIsImV4cCI6MTQ5Mzk3NTQ2NH0.kldUh3H1i3xEiNcxQ2ecq1HsjIIF5BI8Q-tb3sALc3E, content-length=0, accept-language=en-US,en;q=0.8,.......
My question is, how can i achieve the postman header using vuejs. I have tried with axios as well but without success.
Try this way with axios. I'm using spring backend too and it works..
axios.post(
url,
query ,
{headers: {
"header name" : "header value"
}}
)
.then((response) => {
var response = response.data;
}, (error) => {
var error = error.response;
}
}
)

Okta Authentication works but Get User by Id gives Invalid Token Provided

I have a Django app that authenticates using Okta:
headers = {
'Authorization': 'SSWS {}'.format(<okta api token>),
'Accept': 'application/json',
'Content-Type': 'application/json'
}
authentication_payload = {
'username': <username>,
'password': <password>
}
response = requests.post(
<okta auth endpoint>,
headers=headers,
data=json.dumps(authentication_payload)
)
This works successfully. From the response content I am able to get the User Id:
content = json.loads(r.content.decode('utf-8'))
okta_user_id = content['_embedded']['user']['id']
I then use the okta_user_id to create the endpoint to get the okta user by id:
okta_user_endpoint = https://<org>.okta.com/api/v1/users/<okta_user_id>
I then use the same headers from the authentication call, with the same api token, and try to get the user by id:
user_response = requests.get(
okta_user_endpoint,
headers=headers
)
But this is unsuccessful. I get a 401 error with the following content:
{
"errorCode":"E0000011",
"errorSummary":"Invalid token provided",
"errorLink":"E0000011",
"errorCauses":[]
}
Seems straight forward with an invalid token, but if the token is invalid how am I able to successfully make the authentication call? And if the token if valid for the authentication call why is it not working to get the user by id?
Okta recently changed the way that the /authn endpoint works. The /authn endpoint no longer requires an authentication token. This was done in order to support single-page applications.
It looks like your application will need to be able to fetch user information on an arbitrary user. In that case, using an Okta API token makes sense.
However, if you were making that call from a single-page application, you would want to make a request to the /users/me API endpoint.

Resources