Security using Elasticsearch and X-pack in Angular 2/5 - javascript

I'm new to anything to do with user authentication in general, both front and backend. I'm looking in to building an application that uses Elasticsearch with Angular 2/5. There's not a lot of information (I've found some) about how to build an Angular 2+ app with Elasticsearch, particularly in regards to authentication, and user role management. But researching how to accomplish this, I've found this tutorial by Jason Watmore that I will try to adapt to Elastic. I see in the comments, Jason explains that for sites where you want the front-end to be secure, it is advisable to do authentication in a separate front-end app, and then redirect the user to the full app, once the user has logged in. The reason being that no front-end app is secure, in that a user could alter variables to view routes that are protected by route guards, or other ways. That data is still secure from the back-end, but you have features you don't want the public knowing about in the front-end, like how you are analyzing data entered by users.
My first (but secondary) question is, in regards securing a front-end application, is this an absolute truth that it isn't possible? It makes sense, and I have a hunch it is true, but I was wondering if there are ways to at least make it very difficult to view guarded routes. (Like the route guard asks the server if the token is valid?... But then you could just mod the function to always return true, right? Hmm...)
Anyways, it's looking like my application will need three parts in lieu of this. The login/registration, the public side where the standard route guards are sufficient, and an admin that will need to be entirely hidden from the public.
With Elasticsearch, (I think) there's an opportunity to develop our application entirely without backend coding, since X-pack provides security and features for managing user roles... Except for maybe one thing: I'm not sure how to keep the front-end of the admin from the public. Will this require some backend work? Update: This was what someone else was telling me early on. It isn't true.

With Elasticsearch, (I think) there's an opportunity to develop our application entirely without backend coding, since X-pack provides security and features for managing user roles.
It's possible, but not recommended. The Elasticsearch API is not designed to be consumed directly by a front end client, and the security constraints that are put in place within X-Pack do not aim to be secure within that environment.
Elastic recommends that you communicate with Elasticsearch from a backend process.
There are elasticsearch clients for many languages including python and node, so you can use whatever backend technology you prefer.

Related

How to handle client secret in angular code in a public site

I have a problem trying to figure it out for few days, still didn't get any rigid solution.
I have an angular app which will be publicly available so no login or credential is needed to open the website, and user can have an Id as query param. lets' say www.mysite.com/123
to retrieve data for 123, I have a backend, that needs authentication with clientId and clientSecret, to get access_token and then call the api with access_token to get information.
If I put clientId and clientSecret in the code a hacker can steal it and will be using it.
There were some suggestion to enable CORS on backend to make sure only requests from my site will be handled. which I already did, but with knowing the clientId and clientSecret even if CORS is enable a hacker can send requests from postaman by adding origin and referrer as header.
I tried Angular Universal for server side rendering hoping the api call will be run on serve side and will be hidden from user, but api call still happing in front end.
Really stuck in this problem any kind of help is appreciated.
Since the application is small and it's only hosting a web component developed by stencilJs, if other languages such as react or vue can support my scenario I can switch
You can go extensive ways of obfuscating statically inserted token in the frontend client build, yet it is still going to be there and the only thing it will add — extra steps for an attacker to reverse it, at least to my knowledge.
So to explore the solution to your problem, i guess you want to define it in the more narrow way, i.e what are you trying to protect:
resource requiring privilege (admin panel)
then your answer will be dynamic auth.
protect your api from external usage/ddos
CORS, ratelimiting, dynamic token issuing(take notice that strategy still will be available inside frontend client code)
also i think owasp guidelines will be a good read on the topic:
https://cheatsheetseries.owasp.org/cheatsheets/REST_Security_Cheat_Sheet.html
I think i should clarify that in my opinion the solution that you are going to implement in the end in the case of the "protection of the api" is going to be building fences to jump over, rather than sealing api completely from the 3rd party usage.

Hiding API access credentials from an AngualrJS app

This is a design question for AngularJS websites that access a REST API. Since all the AngularJS code can be viewed from the client side (assuming obfuscation is not completely secure) how do you hide the API access credentials (the API key and password or even a JWT)?
This can be extended to a broader question about how other application logic can be hidden in an AngularJS website?
My research led me to some insights, one of which was
http://billpatrianakos.me/blog/2016/02/15/securing-api-keys-in-a-javascript-single-page-app/
But this has me more confused now, since the post suggests an SPA connecting to a REST API is not a good architecture. I thought it was and now can't figure what the right approach is.
The closest I can come to an answer is this resource:
https://developers.facebook.com/docs/facebook-login/security#appsecret
Facebook, is pretty good with their security and say:
Never include your App Secret in client-side or decompilable code.
Use unique short-term tokens on clients.
In short, do not keep API secrets on the client side
Answering the discussion in comments for sake of not being brief:
And then my question would be "what then is the correct architecture for SPAs and server side code (or database access)?".
There's no one correct architecture, it depends on the size and scope of your project. It will also depend on what frontend and backend frameworks you choose. Those choices also will depend on how many other APIs you are calling, or what other developers or you are most familiar with.
Speaking more specifically about security though, ideally you'd like to set up a session for the user which consists of a token that the user uses to identify himself. This is usually generated for each user by the server when they login. Generally this is provided by the framework you are working in, but even if it isn't, it's fairly simple to build. You will want to prevent cross origin requests (making sure the user is actually on YOUR frontend) and have secure connections (setting up SSL and https, though this can get complicated). You will generally want to run your JS code through something like Uglify to prevent it from being too easy to look through, but this does NOT guarantee that people cannot take that code and un-uglify it.
As the other answers have suggested, you should never keep API keys or any secrets in the client source code. There is no way to hide anything on the client, and obfuscation != security.
If you are looking to architect secure authentication/authorization into your app, you will want to return a JWT to the AngularJS application. You can then pass this JWT as a Bearer token to your API which will verify the validity of the token and allow the API to authorize access to the AngularJS application.
As for where to store the JWT token, you can store it in either Local Storage or in a cookie. There are serious considerations between choosing whether to store the token in either of these locations.
If security is your concern, I would look into the OAuth 2.0 Implicit Flow.
Don't put API keys in your client side source code. Keep them on your server, and have your client make a request to YOUR server, which then calls out to external APIs for data.

Securing API with Node

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

Keep an API call private/protected

I'm working on a web app that is mostly static - just HTML/CSS/JS + assets. I'm using a Rack server (Thin, actually) to serve it.
While the app is mostly static, there are a couple of server-side needs that have cropped up along the way. Since the app needs to interact with those needs via JavaScript, I've added Sinatra to the stack to allow me to easily set up some routes to serve as a simple API.
One such API call is to send an email - the web app needs a way to send an email to users. I set up a route (/api/mail) that can be called with a POST that includes a JSON object, and Ruby will fire off an email (via SendGrid).
Here's my issue - by nature, these API calls are public. Most of the time, that is fine - but with the email API, I want to protect it so that nobody can just start sending malicious emails with a simple POST, posing as my app.
Problem is, I'm not quite sure how to authenticate this. The web app itself is the client, not the user, so a password or API key seems worthless, since anyone could just sniff out the POST header and grab the credentials that the app is posting to the API.
Is encrypting everything via SSL my only option, or am I missing some glaringly obvious solution?
At the end of the day, anything you do can easily be scraped. I would do some aggressive rate limiting by ip and session, don't think if anything else would be possible (or effective)

Using OpenID (RPX) (and maybe OAuth) for a RESTful web service

How would you combine OpenID with a RESTful web service?
The personal project I'm working on is using the RPX SaaS to do OpenID. The key result of this is URL describing the logged in user. The app itself is heavily Javascript and I'm planning on using a REST api to communicate with the backend for database persistence and spatial processing.
The security requirements on this application aren't big. I want to know which user is making a request. I don't believe I need to use SSL to be confidential about the data and I don't want the overhead of running SSL.
I'm using Spring and would like to use Spring Security (Acegi) if possible but I'm not wedded to that idea.
Options:
Return the OpenID URL to the Javascript app, use this to retrieve the list of resources for the user and then retrieve/save/etc those resources by id.
Create a session table which connects the OpenID URL with a random session token. Return the token to the Javascript app which must then return the token with every subsequent request.
Use the session from option 2 as the Consumer Token, etc for OAuth. Initially, the session would be sent to the app using PKI encryption.
Rely on J2EE HTTP Session.
Of these options I'm leaning towards option 2. Hijacking the session would be difficult as the attacker would have to guess the session id and I don't believe the application requires protection from sniffing. Option 3 is essentially the same as option 2 but the session id isn't available for sniffing. Option 4 puts the OpenID URL into the server's memory and causes all the scalability problems REST is designed to avoid.
I'm grateful for any discussion on this.
So, 2 years 3 months later I can answer my own question. I implemented this for my personal project and I have separately implemented it for my employer.
Plugging into Spring Security is the best way to go. You can choose to use the pre-authenticated flow but you may find the CasAuthenticationFilter (and CasAuthenticationEntryPoint) work better as they have most of the flow you need.

Categories