I have been thinking over this issue from past few months. Recently, I have started with complete JS Built front-end, where the forms are posted using Ajax.
I have a doubt, how to recognize on the server side, from where the data is coming from. Is it coming from actual form event or it is coming from browser console.?
What I have tried:
Creating a two way handshake: Before posting the form, the Application will contact the server, and the server will send a token inside the cookie, which will be sent back with the form post. But, even if we post by browser console, that cookie will go carrying the token. So, Failed.
Binding Hidden Field: But if someone, is posting the data from browser console, he would definitely look for the hidden fields as well. Basically, he'll replicate my AJAX to send the same request, in the same fashion. FAILED!!
I am not able to figure out this part. Can anyone help?
Thanks in advance.
Rule #1 of programming for the Internet: Never trust anything from the client. EVER.
Rule #2 of programming for the Internet: Never trust anything from the client. EVER.
Rule #3 of programming for the Internet: You can not make the client trustworthy.
I know the first rule is duplicated twice, but it is worth it.
There is simply no way to do what you intend to do.
A person who wishes to send data to your server, via an AJAX request or a POST request, can easily do any of the following:
Modify the form using browser tools or a proxy and force-feed in whatever information he wants.
Capture the entire transaction, through a tool like fiddler2, and change the values and re-send them. No browser needed.
Modify the code running from your site to send (or allow) whatever data he wishes to send.
Use a tool like Curl to fake an browser and send whatever information he wishes to.
There is simply no way of knowing, on your server, where that information came from.
From a security point of view, you simply can not trust anything -- ever.
Validate the credentials, give the user a login token (usually a cookie) and then still be suspicious of everything the client sends you. If there is something that shouldn't be changed or updated, make sure your back-end doesn't allow it to be changed or updated.
We have tons of code in our application that looks like this:
if (user.HasPermission("MayUpdateFirstName") {
record.FirstName = FormData.FirstName
}
That way, if FirstName is passed in, and the user can't modify it, then it doesn't get modified.
Related
I am doing a Website 100% in ReactJS, It's a simple/medium complex, this has a Login, Profile and other sections more. After Users Log into the site the login callback returns some important values like: "Token, UserRole". Currently I'm storing these values in Web client using localStorage .
My doubt is the next: There is a better way to store this values? Because if any person changes the value from the Browser Console this could be a BIG ISSUE because they could change the role and then execute things that they never should do.
I thought to do it with Redux, but if the users Refresh the website then they lost the values, so I am not pretty sure to choose this.
What do you think guys?
TIA!
The general rule is to never trust any data stored client-side, except for an authentication token or the equivalent. All changes that the user makes that involves the server should be verified on the server. So, rather than:
if any person changes the value from the Browser Console this could be a BIG ISSUE because they could change the role and then execute things that they never should do
Instead, the right thing to do would be, when the client wants to do something (such as edit their profile), have the client send their authentication token (or session ID) with the rest of the payload to your server. Have your server examine the token, check that the user associated with the token actually does have the required permissions for what they want to do, and only then continue to process the request.
Whether you also happen to store some information in Redux or elsewhere has no impact.
Storing login-related information client-side is relatively common and isn't inherently bad - just make sure to always verify it on the server when something that requires permissions is requested.
One approach some use is for the server to create an encrypted JWT that only the server can decode, which gets sent with requests.
I have a controller like the image below. This controller hides the relevant record in the database when the fetch request is sent. Do I need to use http post for such operations in this project that I wrote with Entity framework core? The problem with this controller is that the admin executes the javascript code fetch(https://localhost:5001/admin/deletepost?delete=url) on any page. As soon as this get query runs, the relevant record is hidden or deleted from the database. Is it safe as it is? How can I make it more secure? Thank you very much to everyone who replied.
Although this method is only accessible to the admin, will the deletion of the record as a result of the admin sending this request cause a deficit?
For several reasons, POST is more secure than GET.
GET parameters are passed through the URL. This means that the parameters are stored in the server log and browser history. When using GET, you can also easily change the data submitted to the server because it is in the address bar.
The problem when comparing the security between the two is that POST may block temporary users, but it cannot block malicious users. It is very easy to forge a POST request and should not be fully trusted.
The biggest security problem of GET is not the end user's maliciousness, but the third party sending a link to the end user.
Another point is that you must consider where to use GET and POST, because GET should only be used for operations that do not change database information, and only request or read information and POST data should be used when the data will be changed.
Some web scanners will automatically click on each link (usually a GET request) instead of in a button or form (usually a POSTS request) to avoid changing the database, but for example, if you perform a delete operation after the link, you The risk of clicking on the link may be easier with more automated tools.
I'm making a google-chrome-extension for a certain website, and want the browser_action to display the number of notifications a user has received on said website.
Currently, I am using an ajax request to retrieve the HTML from the website/messages page, and then I am using jQuery to count the number of "#unread > li" elements in that HTML (each one representing a new message.)
Now, I take this number and display it on the browser_action icon.
All works perfectly, the correct amount of messages are notified, BUT the user must be logged in on the site (not my site) for it to work properly, otherwise they will think that they have no messages.
I was thinking that I could detect if the user is logged in, and if not display a red ! exclamation mark on the icon. Then, when the user clicks to show the pop-up, it asks them to log in.
However, I have no idea how to actually log the user in to the website using this method: how do I send the credentials across? Or does the website have to support a request like this?
TL;DR
How can I log a user into a website I don't own remotely?
Disclaimer: I've never done a google chrome extension, but based on the rest of your question, it sounds like it's just working with JavaScript like any other web page, so I'll go ahead and answer it.
In any case, working with cookies in JavaScript can be somewhat of a pain:
https://developer.mozilla.org/en-US/docs/Web/API/document.cookie
http://www.perlscriptsjavascripts.com/js/cookies.html
I'm assuming that your server side already works with and expects cookies, so I won't try to suggest any alternatives. That being the case, your server is what needs to validate the cookie, so, IMHO, might as well set the cookie on the server side. If the server handles it, on the JS side, you simply post the username/password to a server-side page, e.g.
$.post("/user/login",{"Username":"foo","Password":"bar"},callback);
That server-side page validates the username/password and then, if successful, generates the cookie and sends a response back to the JavaScript (e.g. {"IsSuccess":true}). Upon receiving a successful response rather than an error, you just start calling the other web services to retrieve your data assuming you are logged in and build out the page.
Assuming that your web services will return HTTP error codes that help you determine a problem with the session, if you get a 401 error code, you take the user back to the login page. If you get a 403 error code, you let the user know they can't access that data...etc., all depending on your app.
Ultimately, JavaScript doesn't know whether a user is actually logged in, so you have to rely on the server to send you information in a way that is understandable so that you can direct/prompt the user as necessary.
[Edit: 2014-11-21]
You didn't answer my other question: what do you get back? If they don't set the cookie themselves at the login, then you need to get back the session token from the response they send...if they don't send you a session ID, you're SOL. If they do send you an session token/session ID, then you need to know what to name it (e.g. PHP uses something like PHPSESSID as the cookie name, but it can be whatever the coders of that domain decided on). Beyond that, you have to be able to set the cookie for THAT domain name (3rd party cookie). This may have mixed results depending on the user's settings--if they block 3rd party cookies--however, since this is a google extension and not a website, maybe it's able to bypass that kind of restriction. I know that FireFox's developer toolbar is able to manipulate cookies for all domains, so it would be a reasonable assumption you would be able to as well.
Before asking the question, I admit that this method is uberly discouraged and not secure. I am aware that to achieve this is through SSL.
However, I am developing an HTML5 apps (and it seems that implementing the SSL approach would take a lot of time) and I would like to know the best way to POST a form content.
i.e I have the following form
<form id="someform" name="someform" method="POST" action="some/server/url">
The way this form is submitted (currently) is using ajax $("#someform).serialize() and so on..
Using this implementation I am facing with (at least) these 2 immediate problems:
User could use tools (i.e TamperData | a firefox addons) to modify the posted content (Interception-and-modify).
User could forge the data by sending 'fake'submission (Forging)
I am wondering if there is somehow I could at least (obfuscate the POST-ed) value.
I came across with this great http://www.jcryption.org/ tools, but not sure how should I implement it to workaround the problem I am facing.
ps: again I am aware that relying on client-side script is way less secure compared with handling all execution from within the server-side.
framework + language I am using is: CodeIgniter + PHP + JavaScript (jquery)
1st Amendment:
I am sure there is at least a work around using this theory
First, I am not too worried about the confidentiality part of my data, that is the POST-ed value will not give any valuable information even if someone else knows what it is.
What concerns me though is the integrity and the authenticity of the POST-ed value. This is simply means that no one else should tamper the information once its being transmitted (once the submit button is clicked), nor anyone could forge or create a fake value (spoofing the server).
This theory leads to digital signature, where (again in theory) I should somehow sign the POST-ed value using server PUB-key, then hash the POST-ed value using the server PUB-key and finally send both the original POST-ed value along with the hashed value.
Prior sending the POST-ed value, the client MUST request for the server PUB-key, so the client can hash the POST-ed value. The server could probably store the PUB-key information along with SESSION information.
Then the server will have to (again) hash (this time with the server PRI-key) the original POST-ed value (sent by client) and compare the two hashed value. If those value is the same, it simply means it is authentic.
Now the part which I am yet to understand is the HOW.....
is there any tools/frameworks/plugins/tutorial/example on how to do this? since it would be too much for me (not to mention the limited amount of time I have) for developing the whole Public-Key-Infrastructure from scratch
Take one step further and realize that a user can encrypt faked data as well.
And SSL won't help against such a tampering.
That's a web-development axiom: everything can be faked on the client side. Period.
So, instead of encrypting anything, just verify your input on the server side, like every other site does.
Use sessions to store the data that a user should have no access to.
User
Spoofed Form Submissions
You will get full info here
I've been looking for better ways to secure my site. Many forums and Q/A sites say jquery variables and HTML attributes may be changed by the end user. How do they do this? If they can alter data and elements on a site, can they insert scripts as well?
For instance I have 2 jquery scripts for a home page. The fist is a "member only" script and the second is a "visitor only" script. Can the end user log into my site, copy the "member only" script, log off, and inject the script so it'll run as a visitor?
Yes, it is safe to assume that nothing on the client side is safe. Using tools like Firebug for Firefox or Developer Tools for Chrome, end users are able to manipulate (add, alter, delete):
Your HTML
Your CSS
Your JS
Your HTTP headers (data packets sent to your server)
Cookies
To answer your question directly: if you are solely relying on JavaScript (and most likely cookies) to track user session state and deliver different content to members and guests, then I can say with absolute certainty that other people will circumvent your security, and it would be trivial to do so.
Designing secure applications is not easy, a constant battle, and takes years to fully master. Hacking applications is very easy, fun for the whole family, and can be learned on YouTube in 20 minutes.
Having said all that, hopefully the content you are containing in the JS is not "mission-critical" or "sensitive-data". If it is, I would seriously weigh the costs of hiring a third party developer who is well versed in security to come in and help you out. Because, like I said earlier, creating a truly secure site is not something easily done.
Short Answer: Yes.
Anything on the users computer can be viewed and changed by the user, and any user can write their own scripts to execute on the page.
For example, you will up vote this post automatically if you paste this in your address bar and hit enter from this page:
javascript: $('#answer-7061924 a.vote-up-off').click();
It's not really hacking because you are the end user running the script yourself, only doing actions the end user can normally do. If you allow the end user on your site to perform actions that affect your server in a way they shouldn't be able to, then you have a problem. For example, if I had a way to make that Javascript execute automatically instead of you having to run it yourself from your address bar. Everyone who came to this page would automatically upvote this answer which would be (obviously) undesired behavior.
Firebug and Greasemonkey can be used to replace any javascript: the nature of the Browser as a client is such that the user can basically have it do anything they want. Your specific scenario is definitely possible.
well, if your scripts are public and not protected by a server side than the Hacker can run it in a browser like mozilla.
you should always keep your protected content in a server side scripting and allow access by the session (or some other server side method)
Yes a user can edit scripts however all scripts are compiled on the user's machine meaning that anything they alter will only affect their machine and not any of your other visitors.
However, if you have paid content which you feed using a "members-only" script then it's safest if you use technology on the server to distribute your members-only content rather than rely on the client scripts to secure your content.
Most security problems occur when the client is allowed to interact with the server and modify data on the server.
Here's a good bit on information you can read about XSS: http://en.wikipedia.org/wiki/Cross-site_scripting
To put it very simply:
The web page is just an interface for clients to use your server. It can be altered in all possible ways and anyone can send any kind of data to your server.
For first, you have to check that the user sending that data to your server has privileges to do so. Usually done by checking against server session.
Then you have to check at your server end that you are only taking the data you want, and nothing more or less and that the data is valid by validating it on your server.
For example if there is a mandatory field in some form that user has to fill out, you have to check that the data is actually sent to server because user may just delete the field from the form and send it without.
Other example is that if you are trying to dynamically add data from the form to database, user may just add new field, like "admin", and set it to 1 and send the form. If you then have admin field in database, the user is set as an admin.
The one of the most important things is to remember avoid SQL injection.
There are many tools to use. They are made for web developers to test if their site is safe. Hackbar is one for example.