I am currently getting an error when making a request to /users/me to receive back my user's data. From what I have been reading, I am not sending the token, though I'm not sure how to store it when I receive it from the jwt/create endpoint when signing in.
This is from my Auth-Test/nuxt-auth/pages/index.vue file:
onMounted(async () => {
const cookie = useCookie('jwt');
console.log('COOKIE: ' + JSON.stringify(cookie));
const response = await fetch('http://localhost:8000/api/auth/users/me/', {
headers: {
'Content-Type': 'application/json',
'Authorization': `JWT ${JSON.stringify(cookie)}`,
},
credentials: 'include'
})
const content = await response.json();
console.log(content);
})
and this is from my Auth-Test/nuxt-auth/pages/login.vue
const router = useRouter();
async function submit() {
console.log(JSON.stringify({
email: user.email,
password: user.password
}))
await fetch('http://localhost:8000/api/auth/jwt/create/', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
credentials: 'include',
body: JSON.stringify({
email: user.email,
password: user.password
})
});
await router.push({ path: '/' });
}
Could anyone help me realize what I might be (am) doing wrong? I can't seem to figure out it myself through the use of documentation after a lot of reading.
In case you might need to access the other files (front and back end), here is the Github repo.
Follow the usage guide here https://django-rest-framework-simplejwt.readthedocs.io/en/latest/getting_started.html#usage
You should store the JWT token instead of using cookie.
const router = useRouter();
async function submit() {
console.log(JSON.stringify({
email: user.email,
password: user.password
}))
const response = await fetch('http://localhost:8000/api/auth/jwt/create/', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
credentials: 'include',
body: JSON.stringify({
email: user.email,
password: user.password
})
});
// it's common to use localStorage to store it so when users go back to your site it's still there.
// If you don't want that you can just store it in memory.
const responseJson = await response.json();
localStorage.setItem('token', responseJson.access);
await router.push({ path: '/' });
}
Then you can use it as a Bearer token
Bearer authentication (also called token authentication) is an HTTP authentication scheme that involves security tokens called bearer tokens. The name “Bearer authentication” can be understood as “give access to the bearer of this token.” The bearer token is a cryptic string, usually generated by the server in response to a login request. The client must send this token in the Authorization header when making requests to protected resources:
Authorization: Bearer 'token'
onMounted(async () => {
const cookie = useCookie('jwt');
console.log('COOKIE: ' + JSON.stringify(cookie));
const token = localStorage.getItem('token');
const response = await fetch('http://localhost:8000/api/auth/users/me/', {
headers: {
'Content-Type': 'application/json',
'Authorization': `Bearer ${token}`,
},
credentials: 'include'
})
const content = await response.json();
console.log(content);
})
Related
I'm trying to create a new user using a pre-request script to be able to use a PUT request to edit user profile settings independently from other requests.
So I'm setting a token from the response to my env variable to use it in the header for the PUT request.
My whole pre-request script is not working - new user is not created and new token is not set. What am I missing?
const createUser = pm.environment.get('url') + 'users'
pm.sendRequest({
url: createUser,
method: 'POST',
header: {
'Content-type': 'application/json',
'X-Foo': 'bar'
},
body: {
mode: 'application/json',
raw: JSON.stringify({"user":{
"username":"{{$randomUserName}}",
"email":"{{$randomEmail}}",
"password": "Pa$$w0rd!"}
})
}
})
pm.sendRequest(function (err, response) {
pm.environment.set("tokenConduit", response.json().token);
});
I think this is incorrect:
body: {
mode: 'application/json',
raw: JSON.stringify({"user":{
"username":"{{$randomUserName}}",
"email":"{{$randomEmail}}",
"password": "Pa$$w0rd!"}
})
}
application/json goes into Headers like you have it, but the body is in raw format. See the example in Postman docs. You stringify a json, so it's just a bunch of charaters, mode "application/json" doesn't exist.
Another thing is you're sending 2 requests, but I think you want to send only one:
const request = {
url: createUser,
method: 'POST',
header: {
'Content-type': 'application/json',
'X-Foo': 'bar'
},
body: {
mode: 'application/json',
raw: JSON.stringify({"user":{
"username":"{{$randomUserName}}",
"email":"{{$randomEmail}}",
"password": "Pa$$w0rd!"}
})
}
};
pm.sendRequest(request, function (err, response) {
pm.environment.set("tokenConduit", response.json().token);
});
So you should have only one pm.sendRequest() in your code.
const createUser =
pm.sendRequest({
url: "https://reqres.in/api/users?page=2",
method: 'POST',
header: {
'Content-type': 'application/json',
'X-Foo': 'bar'
},
body: {
mode: 'application/json',
raw: pm.variables.replaceIn(JSON.stringify({"user":{
"username":"{{$randomUserName}}",
"email":"{{$randomEmail}}",
"password": "Pa$$w0rd!"}
}))
}
})
pm.sendRequest(function (err, response) {
pm.environment.set("tokenConduit", response.json().token);
});
you have to use pm.variables.replacein to use variables inside script section,
Goto console to see what was actually send:
I have an API gateway, which is working from the POSTMAN, using a valid access token, but when I call the same API gateway from inside Lambda function, I am getting 403 access denied error for the same access token. I am not sure where I am missing something. It's really weird, where everything from URL, API_KEY, access token, JSON body is the same, but worked differently in both services.
Please let me know if you have some pointers.
Here is the function that I am using for calling API Gateway -
return new Promise((resolve, reject) => {
var options = {
'method': 'POST',
'url': 'https://XXXXXXXX.execute-api.ap-south-1.amazonaws.com/dev/Patient',
'headers': {
'Content-Type': 'application/json',
'X-Api-Key': 'XXXXXXXX',
'Authorization': 'Bearer ' + accessToken
},
body: JSON.stringify({"resourceType":"Patient","active":true,"name":[{"family":"Smith","given":["Emily"]}],"gender":"female","birthDate":"1995-09-24","identifier":["1221212121"],"managingOrganization":{"reference":"Organization/2.16.840.1.113883.19.5","display":"Good Health Clinic"}})
};
request(options, function (error, response) {
if (error) throw new Error(error);
console.log(response.body);
});
});
Thanks
I have a lambda function which would basically authenticate against the password stored in aws secret manager. The secret manager path would be the username and it will have the value for password. password will need to be passed in the header and username in the query. When I access the url https://{myawsurl}.execute-api.{region}.amazonaws.com/demo/{username} in a browser, I get the error password is missing in the header(which is expected). When I hit the url using fiddler I get 502 all the time.
My api gateway is simply a GET to the lambda function below:
const aws = require("aws-sdk");
const sm = new aws.SecretsManager({ region: 'us-east-1' })
const getSecrets = async (SecretId) => {
return await new Promise((resolve, reject) => {
sm.getSecretValue({ SecretId }, (err, result) => {
if (err) {
reject(err);
}
else {
resolve(JSON.parse(result.SecretString));
}
});
});
}
const main = async (event) => {
console.log("Event: ", event);
try {
const username = event.queryStringParameters ? event.queryStringParameters.username : (event.pathParameters ? event.pathParameters.username : null);
if (username === null || username === undefined || username.trim().length === 0) {
if (username === null || username === undefined || username.trim().length === 0) {
return {
statusCode: 400,
headers: {
"Content-Type": "application/json"
},
body: "username is missing in the url. Please add `/?username={username}` or `/{username}` in the url"
};
}
}
const password = event.headers ? event.headers.password : null;
if (password === null || password === undefined || password.trim().length === 0) {
return {
statusCode: 400,
headers: {
"Content-Type": "application/json"
},
body: "password is missing in the header"
};
}
const secrets = await getSecrets(username);
if (password !== secrets.password) {
return {
statusCode: 403,
headers: {
"Content-Type": "application/json"
},
body: "Incorrect username/password"
};
}
return {
statusCode: 200,
headers: {
"Content-Type": "application/json"
},
body: "User is Authenticated"
};
} catch (e) {
return {
statusCode: 404,
headers: {
"Content-Type": "application/json"
},
body: e.message
};
}
}
exports.handler = main;
My fiddler request is below:
GET https://{myawsurl}.execute-api.{region}.amazonaws.com/demo/{username} HTTP/1.1
password: MyTestPassword
I saw other posts where they mentioned about having a statusCode and body being a string. I have those but still getting error...
I added/removed the headers: { "Content-Type": "application/json"}, from the response and it made no difference..
EDIT: One another thing noticed is whenever I access the api gateway url via browser, it gets logged in my api's log group. But when it is accessed using fiddler it doesn't log. Not sure why...
EDIT: After the suggestion from #ArunK, I used Postman and I found it returns the expected response from the api gateway. I assume some settings in Fiddler may be causing this to happen..
Looks like the issue related to the TLS version supported by Fiddler. You need to include tls 1.0 and 1.2 since AWS API Gateway support these TLS Versions.
From the docs:
A security policy is a predefined combination of minimum TLS version
and cipher suite offered by Amazon API Gateway. You can choose either
a TLS version 1.2 or TLS version 1.0 security policy.
Go to Tools -> Options -> Https and verify the following exists under Protocols - <client>;ssl3;tls1.0;tls1.1;tls1.2
More about Fiddler and Modern TLS Versions.
I am trying to establish a pre-request script in postman but I get error "Full authentication is required" because when I send the authorization in the header it is not being taken into account (As I see in the console).
This is strange because when I use that same header in a separate request it works fine and generates the desired token.
This is my pre-request code:
var username = pm.environment.get("username");
var password = pm.environment.get("password");
const echoPostRequest = {
url: myURL(I deleted due the security reasons),
method: 'POST',
timeout: 0,
headers: {
"Content-Type": "application/x-www-form-urlencoded",
"Authorization": "Basic xxxxxxxxxxxxx"
},
body: {
mode: 'urlencoded',
urlencoded: [
{key: "grant_type", value: "password", disabled: false},
{key: "username", value: username, disabled: false},
{key: "password", value: password, disabled: false}
]
}
}
pm.sendRequest(echoPostRequest, function (err, response) {
console.log(response.json())
//console.log('Saving the token ')
//var responseJson = response.json();
// pm.environment.set('access_token', responseJson.access_token)
});
thank you very much for helping me with this!
I have an app with react and Django rest framework. I use Django allauth for login and registration. when I want to log in, everything is ok, and the response is 201 but the data is empty and I don't get token. I send this request with the postman and I get the token. what should i do?
React Request:
axios({
method: 'post',
url: 'http://localhost:8000/rest-auth/login/',
data: {
username: 'admin',
email: '',
password: 'admin123456'
},
headers: { 'content-type': 'application/json' }
})
.then(response => {
console.log(response.data.key);
})
.catch(error => {
console.log(error);
});
the response is:
{data: "", status: 200, statusText: "OK", headers: {…}, config: {…}, …}
postman request: http://localhost:8000/rest-auth/login/
{
"username": "mahtab",
"email": "",
"password": "mahtab23"
}
postman response:
{
"key": "f75b9f54848a94ac04f455321118aff5d5a7e6f8"
}