Is there a way to hide credentials, such as password or authentication header tokens from user 's eye in a pure HTML/Javascript app?
The AngularJS App communicates against a rails backend via CORS running on a different domain.
Beside setting up CORS being more restrictive or checking against Domains in request on backend side, I wish to send auth tokens or add tokens to headers.
Does anyone know?
kind regards,
Alex
You can only restrict what your user sees by obscurity, which is not a very good Idea.
The key here is to set up your authentication in a way so it does not matter what the user can see or manipulate. One way to do this, is to send generated keys to your client and to your second server app every time your app needs to be authenticated. Restrict usage in a way that makes sense for your app. Another possibility would be registration.
A possible workaround would be to use one server as the only node the client is talking to while the server does all the work of talking to your other server. Especially if you don't want to give your user the possiblity to call the api of your second server outside of your app logic for some reason.
I don't think there is any way out. A smart user can get to it anyways.
Related
There is a sensitive page in my website, so I want to authenticate visitors before they opening a link like: www.examples.com/builder.
I know if I use cookie based authentication everything will be simple, as the browser will send the credential message in cookies automatically. But in my situation, I have to use token based authentication. Browser don't send token if there is no pre-load script.
So my question is how to achieve token based authentication when someone open a sensitive page directly.
As far as I can understand,
you're looking for a way to avoid double roundtrips to send authentication headers to your web-service.
If I am correct, then this would only be possible via service worker which is a not widely supported feature. https://developers.google.com/web/fundamentals/primers/service-workers/
If, depending on your requirements, you can't go for service workers, then, the only left option is to use cookies.
I normally have a secondary authentication flow which uses cookies allowing a web service to authenticate a user on its first get request (the one made by the browser).
There are also some spa framework which implement routing resolvers but this will require a double roundtrip (1. load javascript, 2. send the token).
I'm a regular reader here at stack overflow but this is my first question.
I'm developing an authorization-server using the OAuth2 specs. And I just got stuck with how do I ensure the first-party client authenticity while using the password flow. I read many forums and this is what I got:
Javascript single-page clients
This blog post by Alex Bilbie, he states that to avoid the client_secret problem we should just:
It’s simple; proxy all of your API calls via a thin server side component. This component (let’s just call it a proxy from here on)
will authenticate ajax requests from the user’s session. The access
and refresh tokens can be stored in an encrypted form in a cookie
which only the proxy can decrypt. The application client credentials
will also be hardcoded into the proxy so they’re not publicly
accessible either.
But now this proxy can be accessed by someone impersonating my
angular app. And then I came across this blog post from Andy
Fielder: How Secure is the OAuth2 Resourc Owner Password Flow
for Single Page Apps. He basically says to rely on CORS to
avoid impersonating JS clients.
It is a good idea to use both approaches to secure my JS app?
Native Apps (Desktop and Mobile)
In the case of mobile apps, I only found cases for Authorization
Code and Implicit flows. This is not what I want, as the redirects
will compromise the user experience. So my thoughts on this is:
I will use the ROP flow and then register the client with a
client_id generated for this particular installation and attach it
to the user account, receiving the access_token and a
client_secret as response. Any other token request made by this
client MUST carry this credentials (as the client_id is specific
for the installation, I will be able to check if this client is
already authenticated). This way if someone uses any credential for
impersonating a client, or even registers a bogus client, I can take
mesures to revoke the user and client access.
I know that this can be overthinking, and I also know that some of this matters doesn't avoid anything. I just feel that is my job to protect my API as much as I can.
I would really appreciate your thoughts about this matters! Am I really overthinking? Should I just use the concept of a 'public client' and carry on?
Thank you all and happy coding!
First of all, this problem is not a common priority because most applications are developed first with website, and after with the API. This is probably the reason because no one knows how to deal first clients with oauth2, because everyone have developed other ways to do that and oauth2 is needed only to grant user access to third party applications.
Even if you have develop the oauth2 authorization server only for your first clients applications (thinking about a single authentication mechanism instead of developing many), you should try to develop the authorization code or implicit grant types. You will realize that you need a way to check what user is actually logged in.
The two common methods are:
user session (based on Cookies)
user access from localStorage (based javascript)
In either ways you need to check your application security, user session is vulnerable to CSRF, localStorage are vulnerable to XSS. There are a lot of articles about how to secure your website against either, so I will not suggest anything here, you just need to know that they exist.
Now that you choose your authentication method we can start to do some consideration about:
Javascript single pages applications
Proxy
Having a proxy that filter all requests in my opinion is like to have a door with the keys always inserted. It's useless even build the door.
However, for session based authentication it's the only way to do it. Allowing session authentication on your Rest API will open to CSRF security issues, so you need to have a proxy layer that get the user session, retrieve the access token from the session and do the request to the Rest API adding the Authorization header.
CORS
With this method you need to store the user access token in the localStorage, because the token is retrieved from the Js client directly.
Using CORS you are sure that other websites cannot do requests to your Rest API from a browser. But your first client need to be public (ie: it does not have a client_secret).
Native Apps (Desktop and Mobile)
In my first application I tried to use the same mechanism that you suggest to secure the auth flow. However that type of mechanism require that you identify every user client in an unique way. This is not possible in iOS for privacy reasons and with some probability it will denied in the future releases of Android. So you should rely on a public client and add only the client_id in your native application code.
This means that your native app client/your js client can be impersonalized? Yes, and there is no way to prevent this with oAuth2 resource owner password credentials grant type.
The main reason about this is because oAuth2 is not for authentication, only for third-party authorization, and that grant type was added only for specific third-party applications trusted enought to use directly the user password. You could read more about this argument here and here.
At the end
You still need a way to auhorize your user, and I think that the best you can achieve using oAuth2 is what Auth0 did.
Essentially this Saas manage your users with an oAuth2 server + OpenID connect, so you are always managing your users like its a third-party application and everything works fine.
Indeed, you can see on this page that for mobile applications they suggest to use a browser based login form, because the native one can be impersonalized by everyone that decompile your application, but if you wrap it into an authorization code flow it works fine.
I'm trying to build my first API to be consumed by a mobile application built with Ionic.
Before starting I'm looking into the architecture and I can not understand exactly how to make secure my API routes.
Let's say I have an endpoint like http://myapi/v1/get-items and my application doesn't need an user to be authenticated to view those items in the mobile app.
How should I protect that route from external queries, using Postman for example?
I wish that route to be not accessible unless is not requested by the application.
Looking on Google I can find many solution using basic authentication but all of those require an user to log in... What if my app doesn't have users to log in?
I'm a bit confused but I think there is a solution and I don't know it yet...
I hope you can help me to understand it.
EDIT:
My Question is totally different from the following: How to implement a secure REST API with node.js
I'm looking for solution that DO NOT require a User Authentication.
If you don't want to use User Auth through something like Passport then you can institute a whitelist in your Node API instead. express-ipfilter is an express middleware module that allows you to filter requests based on the request IP.
Requiring a login would be the cleanest and safest way to make sure your api remains private. However, if you want to keep external users out of your services without requiring a login, you will need to "sign" your requests. By that I mean doing something like encrypting a current timestamp on the client using a key known to both the server and the client app, adding that encrypted string as a header, receiving that header in your server, decrypting it and checking that it's not too old of a timestamp before you return a response.
It's not really safe (if someone can see the code they can see the encryption key) but it's an obstacle and it down't require logging in. See this for an example on encryption/decryption
I am building my first node.js webapp. I don't need to manage users registrations. I just need an admin page wich easly allow updating the content of some pages.
I have almost finished the development phase but there is something about security I would like to clarify.
ADMIN PAGE: there are 2 level of security:
1) The admin page is linked to mywebsite.com/hexadecimal_string .
Maybe it's very stupid but the admin page is a "secret" page. Linking
it to mywebsite.com/admin is too much common. Do you think that using
an hexadecimal string can be considered a first level of security?
2) Of course there is a password for admin, stored in my database. If
the password is right, a temp cookie is setted. Maybe I should
encrtypt this password while is posted but I'm not planning to use
https. Is there a way, different by using https, to make the posting
of the password more secure ?
CORS: I don't need CORS but there is a thing that is making me crazy:
In the homepage everyone can post some data to server (we are talking about newsletter emails and others personal datas)
suppose someone reads the javascript code of the home page(in particular the ajax urls) in same way and he tries to post data to the same urls but using a personal script that skip the validation phase. Of course I did the validation to server also but I'd like to not accept any req coming from personal scripts written by other than me. The server should respond only to requests coming from my javascripts, tha anyone can run accessing to www.mywebsite.com. All other requests coming from different scripts will recieve 500-server error.
Now, I read about lot's of people that is tryng to ALLOW CORS. So I was supposing that cors is disabled by default but I tried to post data from another website to mine and the data have been sent without problem and the server responds 200. Why? Can I manage this thing?
There are other common things that I need to analyze and manage for security in my situation??
Since you don't want to use https and are looking for an alternative to that I presume you don't want the password to be sniffed in transit. I suggest a simple encryption decryption algorithm might work out for you. For the second issue, you can add a validation string which the client JS will pass along with other parameters while hitting your server API's. If you generate this string each time the client loads some specific page, then duplication of string will also be tackled.
In case you don't want at all to maintain any sort of db on server side, then attach a hidden HTML field to the API hits. This hidden field again you can encrypt and sent. If you broadcast this field periodically from the server, replication of the field will not be possible.
Also in CORS, you cannot request for data from a cross domain. CORS block comes in place when the browser gets a reply back from the server. Only posting of data does not cause any issue.
I'm developing a single page app with Backbone.js and I was asking myself some question.
When I'm developing an app that relies on render pages on server I do know how to show some parts or not depending on the user is admin or not (just an example).
But now, I'm using Backbone.js and underscore templating to create the views... so.... I could create a cookie that says... ok... is the admin, but anyways, someone smart-enough could just change the cookie value. I'm able to solve it just creating a check in the server side that the user is allowed to do that.
Other chance I'm thinking about is to ask the server for this concrete pieces of code and just paste them in the right site
What do you think?
Thanks
Your scenario is not entirely clear to me, but in general: If the server divulges "secret" information or allows restricted actions without having verified itself that the user is allowed to see something/do something, that's a security hole. Authentication will have to happen in the established ways: user logs in on the server and receives a secure (enough) token, e.g. a session cookie. The server then only sends information that the user is allowed to see to the client and only allows actions the user is allowed to do.
Anything client-side is always, by definition, insecure. A secure client-side-only authentication system does not exist. The server must not take the client's word for who he is. No critical action must be performed on the client without the server being able to verify that action.