How to process sensitive data in single page apps - javascript

I need to understand and maybe ideas about single page apps.
I want to create a project, i'll do it with MVC. I also want to use AngularJS for client side programming.
I know that AngularJS is good for single page applications and when working with SPAs you send your data to API to process. But data sent from Angular is visible to user and open to be manipulated.
I don't want users to be able to see any data or access to the API from the internet. Witch way i should follow?
I'm thinking about keeping sensitive user data in MVC controller. For example let's say user Id is very sensitive for my project. If i keep user id in javascript variable, when i'm sending it to API with some command user will able to change the id and manipulate the system. But if i keep user-id in MVC controller, via user authentication, and send request to my MVC controller then the user won't be able to change it. But i know this is not the best way of doing things, there must be a more clever way.
I'll be glad if someone can explain how this things works in SPAs or when you use Angular and MVC together.

This won't work, you can't prevent user from tampering the data, crafting custom request and doing whatever she wants at her side.
What you should do is to never trust upcoming data - which means validate every incoming id twice, once when you produce it and then when it comes back. Either it comes plain and you verify if it's legal or you encrypt it so when it comes back you decrypt it.
Some data can be stored at the server side, the id you mention is such example. This way user never sees the data, what you pass is the session id which is a long random value, rather impossible to craft. This approach comes with the cost of server side resources that are used, the more users the more resources at the server stored between requests.

Related

Flask API to provide JSON files to a simple HTML+JS+CSS webapp while keeping it secure

I've made a simple webapp that is going to show some data in a table, which will be updated weekly.
This update it done in the backend with some python code, that scrapes and alters some data, before putting it in a SQLite database.
After doing some reading I learned that to deliver that data to my webapp I should make a API with Flask, that can take that data and deliver it to the JS in my webapp in form of JSON, which then can use the data to populate the table. However, I should secure my API with username and pw. But as its a JS frontend that will retrieve data from the API, there is really no point, as the username and pw will have to be hardcoded into JS, which then can be read by the users. (I think)
Should I expose my API to everyone, or is this not the way to go to be able to use SQLite data as a backend for my webapp? I am fine keeping the API to a GET only.
You are correct, it is pointless for you to secure your API. Securing an API is only needed in certain circumstances.
If you are accessing data that you don't want anybody to see, perhaps through a backend call, then it would make sense to add in some form of security (normally an API key or Authorisation tokens in your request headers).
However, if you are making calls from your front-end (i.e. client side) to a backend API, then there is no point putting additional security there as the user can already see the request and already has access to the data the API is returning - so by securing it you are achieving nothing.
Normally, if the page the user is visiting contains sensitive data that you don't want everyone to see, you would take steps to secure your website instead (for example protecting it with a login for username and password before you can access that page). If you were to take this approach, where the website is protected by username and password, then you can update the API to make sure it does not respond to requests where the user is not authenticated (e.g. by generating a session token or something unique for each logged in user).
If you have a look around on websites that have lots of free data available, you will find they all have front end API calls that are completely unsecured (because it is pointless if the data is already free to access). Some websites do take steps to try to make sure it is their own website that is calling the API, but even then it is a bit pointless as web scrapers can always extract the data from the HTML.
Take a look at this page which outlines authentication headers. This simpler route is to hard code the header info in Flask to make it a little more secure. You could also try the more involved route of reading header info from your db. What's currently working for me to read from postgres db is below so you may modify it slightly for sqlite.
def valid():
headers = request.headers
auth = headers.get("X-Api-Key")
user = User.query.filter_by(apikey=auth).first_or_404()
print('from search of db ',user,'',auth)
return str(user)
As you mentioned, you plan to show a public data - then it can be used even
without authentication. Otherwise I think it can take too much unnecessary time spent on that.
As you have just a simple and single table from database, I believe that you don't need an API. You can just create HTML template and render it with data. Some examples can be found here and few more here.

Implement Authorization in AngularJS

I want to implement authorization in AngularJS. In my project which is some kind of social media, different roles or even same roles may see a view file differently.
For example imagine we have two different roles: customer and company.
A customer and a company may have different things in a shared view file, for example a company can have rate on his profile while a customer can't. (different roles).
Or a customer may see a button in a page while another customer can't. (same roles)
As you can see I can't implement authorization by simply checking the roles, and in some situations I need to communicate to the server.
I have multiple choices:
Create a variable in my controller's scope with corresponding permissions, which they have default value of false:
$scope.auth = {
canRate: false,
isConnected: false
};
Then connect to server and change the value of auth object based on the response. And use ng-if in my view files to show or hide elements.
Create a directive and pass comma-separated permissions to it.
<button auth="canRate,isConnected"></button>
Then connect to server to check the permissions. If all of them where true, then show the element.
Use resolve: {...} and get all necessary data from the server when routing, which increases loading time of each page.
I want to know is there a better approach to solve this problem?
Any kind of help or comment would be greatly appreciated.
Note: Of course I have server side authentication and authorization! I just want to show some elements in a view file based on user roles or some other conditions which I explained. And this elements are something like a button or a link, otherwise instead of using a shared view and hiding elements, I could use different views for each situation.
Any how, I know this approaches are for display purposes only, and they can not solve security challenges.
First things first, I LOVE AngularJS. But, like all web client frameworks, in a strict sense you can't implement Authorization in AngularJS.
You can not trust the web client to hide data from the user. If the server sends the data to the client, they can still find a way to see it (using fiddler for example) even if you use ng-hide to avoid displaying it.
So, you must implement Authorization on the server side. Now then, assuming you do that:
AngularJS is great for building dynamic web interfaces based on the data you receive from the server. So, your server should only send the data your client is allowed to see. Then, you can use ng-hide or ng-if to avoid displaying the components that would otherwise show that data.
Furthermore, your server can even send an object that contains the list of possible actions available to the user. And then you could use ng-hide in your buttons so as not to show them when the action isn't available.
Even still, you will need to code your server side to ignore actions that the user isn't allowed to take.
Your approach will work, but it is not secure. I would make sure that the server handles the authentication as well. Personally, I've always used a server-side token based authentication system when working with AngularJS.
Instead of using ng-if, you should make your GET or POST requests require the token given on login. From there the server can determine whether or not to allow the request to succeed, with no chance of the user faking credentials. Both of your examples work fine, but use them as a means to hide things for display purposes only. The web client will NOT keep sensitive information safe or prevent the possibility of POST requests from unwanted users.

Clientside PostgreSQL Javascript access without serverside part

I know that direct access to a database via Javasript is not recommended, since the user would get the database login and thus the ability to manipulate the database.
But in my case, the user cannot see the client-side code, since it's a phonegap app.
Is there a way to do it? And it not, what is a good way to do with a serverside part?
its really not recommened to access database from client-side its not only for security reasons, but what if you changed the database access or upgrade to different database, so you will have to change it in your app which you may not be able to access again after users installed if its mobile app and then you stuck to your database for ever,
so whatever you want to do you can add an action in server-side and depend on your params it will formulate your Query,
for example sending parameter for user=true this will search for users tables, sending parameter for account=true will search in users-accounts tables and so on.

HTML request obfuscation in the event of external APIs with passkeys

So assume I'm using some external API, where I'm required to send it an ID and passkey such as http://whatever.com/api?id=asdfg&key=_hjkl&request=whatever
I'm going to need to have that ID/key stored somewhere and I could get away with not exposing it to the user by putting it in a database or something, but whenever the request is actually shot off is there no way to hide it?
No, there isn't.
If you want the client to authenticate against a service, then the client has to have the authentication credentials. Anything you give to the client, you also give to the user of the client.
If you want to add some kind of protection, then proxy it though your own server or use a time limited token - but keep in mind that anybody can still hit the appropriate end points to get access.
If you are giving data to the client, then you are running a public API and it is best to think of it in those terms.
If the api provides a POST method, you can use that, without having to show the parameters.
Using POST method to hide URL parameters

Asp.net MVC 3 Filter Data then pass into JSON

I am using asp.net mvc 3 and was wondering is it better to pass all the data via JSON and then use javascript to filter the data or is it better to filter the data and then pass it into JSON?
If filtering the data and then passing it as JSON was the best option how would I go on doing this?
If you are looking to filter your data for security reason I suggest you to do then on both side.
You could use jquery validation like jquery.validate() pluggin and best practices find in this web site : https://www.owasp.org/index.php/XSS_%28Cross_Site_Scripting%29_Prevention_Cheat_Sheet
On the server side you must verify and type all data you recieve and all data you send if you are displaying data inserted by users.
MVC is secured with some process (like detection of maliscious data and antiforgery token) but control your data is always better ;).
Well, it really depends on what you are trying to do. There are two possible cases that I see.
In the one case, the date you are sending to the user should only be seen by that user, or needs to be filtered ahead of time so that the user does not gain access to data that they shouldn't. In this case, you definitely want to filter server side and leverage the credential/security system provided by ASP.NET for authorization to the data.
A second case is where you want to keep the amount of the data small. For example,it is not typically a good idea to send huge amounts of data back and forth between client and server side. In this case, you can leverage the power of technologies like LINQ or SQL to rapidly get the data and send it back client side.
In the third case, you would want to send as much data as you need (and no more) to the client to allow for good client/UI interaction. That way, you can perform quick filtering, searching, or whatever client-side activity is needed. This can greatly improve user experience.
In general: limit the total amount of data you send, don't send anything the user shouldn't see (even if you aren't displaying it), and do as much work as you can client side to improve the user experience.

Categories

Resources