I have just started learning React Native. Built my Component and am trying to use an authenticate function written in a separate file to authenticate.
My Authenticate file looks like
var constants = require("../constants")
module.exports = function(usr,pwd){
var trailing_url = '/api/token/';
var url = constants.DOMAIN + trailing_url;
console.log("url");
return fetch(url, {
method: "POST",
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
body: JSON.stringify({
username: usr,
password: pwd,
})
}).then(function(response){
return response.json();
}).then(function(json){
return json;
});
}
I am experiencing this error once i go to fetch. I am unable to make network requests to my backend in django which is running at http://127.0.0.1:8000/api/token/
I am getting the following error. Couldn't copy paste that here for some reason.
Another question I had is how to debug the code? I tried the Chrome debugger.
But its showing
Status: Waiting, press Ctrl R in simulator to reload and connect.
Tried refreshing the Simulator but didn't work.
Thanks Ashutosh for pointing that out. I didn't notice that since the emulator is a different machine, it wouldn't actually recognize localhost or 127.0.0.1
The problem was i was using the local machine's Loopback IP Address when requesting for data.
Related
When trying to upload a selected image from my React Native project I get a nondescript error message:
Network request failed
Seems to be a common issue, but most people are just forgetting their file types or are on Android and have an issue with Flipper. Nothing that has worked for anyone I've found with the same symptoms has worked for me.
Code:
const localUri = result.uri;
const filename = localUri.split("/").pop();
const type = mime.lookup(localUri) || "image";
const formData = new FormData();
formData.append("file", { uri: localUri, name: filename, type });
try {
const file = await fetch(`${SERVER_URL}/api/upload`, {
method: "POST",
body: formData,
}).then((res) => {
console.log(res);
return res.status === 200 ? res.text() : res.json();
});
} catch (e) {
console.log(e);
}
Considerations:
Using a physical IOS device. Iphone.
Using Expo 40.0.0 with corresponding RN SDK, not ejected.
Using expo-image-picker to get image.
Using NGROK to get requests through to my localhost server from my phone.
All other requests to my server from React Native work fine, it's only when I try to uplaod a file
Image renders fine from supplied URI, so it's getting the right source.
Form Data source from above:
{ "name": "CAPS-FILE-NAME.jpg", "type": "image/jpeg", "uri": "file:///var/mobile/Containers/Data/Application/CAPS-PATHING/Library/Caches/ExponentExperienceData/project-src-pathing/ImagePicker/CAPS-FILE-NAME.jpg", }
Things tried:
Using Content-Type header: "multipart/form-data"
Using /private instead of file://
Using Postman to hit my server through NGROK, which works
Changing my Expo/RN to 38.0.0
Getting base64 -> blob -> formData, same result
Many other things I've forgotten now. If it's on Google results, I've tried it.
For anyone who gets stuck with this also, I switched to using XMLHttpRequest instead of fetch and it miraculously works now. Not sure why fetch is broken in RN, but at least there's a solution.
I was wondering if someone could bring some light on how GET request paths work. I am not skilled in networking so am a bit lost here.
I have a Flask app running on PythonAnywhere... I built a small app with Vue and am using Axios for send GET request to my API on server. I however found out that when I run my app on PythonAnywhere server i will get response only when I also run the flask app on my local machine. I suspect it is due to me trying to send the request to http://localhost:5000/api/random2. Is that true? What do I have to replace it with to send the request to my PythonAnywhere app?
getResults () {
const path = `http://localhost:5000/api/random2`
axios.get(path, {
params: {
p_a: this.p_a,
R_eH: this.R_eH,
a: this.a,
b: this.b
}
})
.then(response => {this.result = response.data})
.catch(error => {
console.log(error)
})
}
},
Thank you,
Jakub
I m new to loopback and don't know how to do following things in loopback
I want to set access token and other value in a session using middleware for that I found this thing in server folder of loopback
"session": {},
in middleware.json but don't know how to use this because there is not much documentation
I want to condition in session middleware like if I has session value then continue else throw to login page
note i already install this npm install express-session
Could you be a little more specific about what you want? but I'll explain a little bit about how authentification sessions are handled, there are two native ways you treat it all; The first one would be using a more raw reading pulling for modeling of your api and the second would be to use the JWT in aligned with accessToken and Passport.JS.
There are two examples available today with Loopback 3.x
loopback-example-user-management
loopback-example-passport
Basically using the raw reading with app.post('/login', function(req, res) then if your client is successfully authenticated you generate a cookie using your client's accessToken, example res.cookie('access_token', token.id, { signed: true , maxAge: 300000 }); res.set('X-Access-Token', token.id); and finally if you want you can transport the generated token to your pages:
res.render('home', {
email: req.body.email,
accessToken: token.id
});
Now with Passport.JS a middleware is used to secure all your connection and authentication:
app.middleware('session:before', cookieParser(app.get('cookieSecret')));
app.middleware('session', session({
secret: 'Seal Playing Saxophone',
saveUninitialized: true,
resave: true,
}));
passportConfigurator.init();
One of the authenticated page rendering pillar is var ensureLoggedIn = require('connect-ensure-login').ensureLoggedIn; you can use this ensureLoggedIn('/login') to free up your routes:
app.get('/auth/account', ensureLoggedIn('/login'), function(req, res, next) {
res.render('pages/loginProfiles', {
user: req.user,
url: req.url,
});
});
Now if you just want to skip this all and already have your environment set up and just want to create a route to get the accessToken of the logged in client use the template below;
app.get('/session-details', function (req, res) {
var AccessToken = app.models.AccessToken;
AccessToken.findForRequest(req, {}, function (aux, accesstoken) {
// console.log(aux, accesstoken);
if (accesstoken == undefined) {
res.status(401);
res.send({
'Error': 'Unauthorized',
'Message': 'You need to be authenticated to access this endpoint'
});
} else {
var UserModel = app.models.user;
UserModel.findById(accesstoken.userId, function (err, user) {
// show current user logged in your console
console.log(user);
// setup http response
res.status(200);
// if you want to check the json in real time in the browser
res.json(user);
});
}
});
});
I hope I have illuminated your ideas :] I am here to answer your questions.
Hello i have deployed my project in ionic view where i need to make a http call to remote server.I have implemented proxies like this
{
"name": "MobileUI",
"app_id": "608c237d",
"type": "ionic-angular",
"proxies": [
{
"path": "/Auth",
"proxyUrl": "https://example.com/Auth/Authenticate",
"rejectUnauthorized": false
}
]
}
And I make a login call to the from the provider like this
AuthenticateUser(username: string, password: string) {
var userNamePwd: any = {};
userNamePwd.username = username;
userNamePwd.password = password;
let body = JSON.stringify(userNamePwd);
let headers = new Headers({ 'Content-Type': 'application/json' });
let options = new RequestOptions({ headers: headers });
return this.http.post('/Auth', body, options)
.map((res) => {
let data = this.extractData(res);
this.storage.set('id_token', data[0].Token);
this.sharedAuth.SetEntityData(data);
return data;
})
.catch(this.handleError);
}
The Login works perfectly when testing in web browser but when i upload the app in my ionic view i am getting this error response with status 0 for url null
I implemented the proxies in the way mentioned in http://blog.ionic.io/handling-cors-issues-in-ionic/ .
Am I missing something ?
the issue is that when you run the app in ionic view app, there is no local proxy to forward requests to your backend. So you get into cors issues because the local webview enforce strict cors in the ionic view app.
I hope the ionic team comes up with a fix. As for now, to my best knowledge, you should modify your backend to allow all origins, or use a web server as a proxy to forward your request to your api servers.
I am trying out the new Fetch API but is having trouble with Cookies. Specifically, after a successful login, there is a Cookie header in future requests, but Fetch seems to ignore that headers, and all my requests made with Fetch is unauthorized.
Is it because Fetch is still not ready or Fetch does not work with Cookies?
I build my app with Webpack. I also use Fetch in React Native, which does not have the same issue.
Fetch does not use cookie by default. To enable cookie, do this:
fetch(url, {
credentials: "same-origin"
}).then(...).catch(...);
In addition to #Khanetor's answer, for those who are working with cross-origin requests: credentials: 'include'
Sample JSON fetch request:
fetch(url, {
method: 'GET',
credentials: 'include'
})
.then((response) => response.json())
.then((json) => {
console.log('Gotcha');
}).catch((err) => {
console.log(err);
});
https://developer.mozilla.org/en-US/docs/Web/API/Request/credentials
Have just solved. Just two f. days of brutforce
For me the secret was in following:
I called POST /api/auth and see that cookies were successfully received.
Then calling GET /api/users/ with credentials: 'include' and got 401 unauth, because of no cookies were sent with the request.
The KEY is to set credentials: 'include' for the first /api/auth call too.
If you are reading this in 2019, credentials: "same-origin" is the default value.
fetch(url).then
Programmatically overwriting Cookie header in browser side won't work.
In fetch documentation, Note that some names are forbidden. is mentioned. And Cookie happens to be one of the forbidden header names, which cannot be modified programmatically. Take the following code for example:
Executed in the Chrome DevTools console of page https://httpbin.org/, Cookie: 'xxx=yyy' will be ignored, and the browser will always send the value of document.cookie as the cookie if there is one.
If executed on a different origin, no cookie is sent.
fetch('https://httpbin.org/cookies', {
headers: {
Cookie: 'xxx=yyy'
}
}).then(response => response.json())
.then(data => console.log(JSON.stringify(data, null, 2)));
P.S. You can create a sample cookie foo=bar by opening https://httpbin.org/cookies/set/foo/bar in the chrome browser.
See Forbidden header name for details.
Just adding to the correct answers here for .net webapi2 users.
If you are using cors because your client site is served from a different address as your webapi then you need to also include SupportsCredentials=true on the server side configuration.
// Access-Control-Allow-Origin
// https://learn.microsoft.com/en-us/aspnet/web-api/overview/security/enabling-cross-origin-requests-in-web-api
var cors = new EnableCorsAttribute(Settings.CORSSites,"*", "*");
cors.SupportsCredentials = true;
config.EnableCors(cors);
This works for me:
import Cookies from 'universal-cookie';
const cookies = new Cookies();
function headers(set_cookie=false) {
let headers = {
'Accept': 'application/json',
'Content-Type': 'application/json',
'X-CSRF-Token': $('meta[name="csrf-token"]').attr('content')
};
if (set_cookie) {
headers['Authorization'] = "Bearer " + cookies.get('remember_user_token');
}
return headers;
}
Then build your call:
export function fetchTests(user_id) {
return function (dispatch) {
let data = {
method: 'POST',
credentials: 'same-origin',
mode: 'same-origin',
body: JSON.stringify({
user_id: user_id
}),
headers: headers(true)
};
return fetch('/api/v1/tests/listing/', data)
.then(response => response.json())
.then(json => dispatch(receiveTests(json)));
};
}
My issue was my cookie was set on a specific URL path (e.g., /auth), but I was fetching to a different path. I needed to set my cookie's path to /.
If it still doesn't work for you after fixing the credentials.
I also was using the :
credentials: "same-origin"
and it used to work, then it didn't anymore suddenly, after digging much I realized that I had change my website url to http://192.168.1.100 to test it in LAN, and that was the url which was being used to send the request, even though I was on http://localhost:3000.
So in conclusion, be sure that the domain of the page matches the domain of the fetch url.