views:

73

answers:

5

I just had this thought, I don't know if I am slow though.

Usually, I store the id of the item I am editing in a hidden field. Then in backend (I am using PHP/Zend Framework btw), I get it to determine which item gets edited. But then I thought, in something more secure, eg. edit profile, the user can somehow edit a hidden field right? Then he can edit someone else's profile. I know for edit profile, I can get the id form the session variable, but what if i got something that requires me to store the id somewhere?

I got ACL (Zend_Acl) I do this. Basically grab the id from the request params

$id = $req->getParam('id');

then check if the logged in user is allowed to edit the item. But the thing is I wonder if the url is something like /users/edit/1 where 1 is the id. But somehow, the hidden field is changed to 2, what will the request param be?

How would you deal with this?

+1  A: 

Storing ID in hidden value isn't quite safe. Generally, we store ID in session variable.

ppshein
There's no need to use the session variable. It's more semantically sound (and easier) to check that user posting data has permission to edit the record they're posting data for.
meagar
ah. meagar, u phrased what i thought very well! having 2 variables that supposedly shld store the same value, is messy and maybe prone to errors
jiewmeng
The OP is asking how to determine what the record being edited is without it being changed, i.e how they store the ID to then post back to the server to query the record with, therefore ppshein's statement is correct. You would store the ID in a session so it can't be changed and THEN check the permissions for that record. You can't check permissions if you don't know what document is being edited.
webnoob
@webnoob I some times open several tabs of stackoverflow with several answers/questions on the same time. You can see, that without doing loops in the air, your solution enables only one open window/tab of an edited product. Not very user friendly.
Itay Moav
@Italy Moav Good point. On that note, surely the only true way of handling that then is to store the encrypted ID that is being used on the client side so it is posted back to the server because any way of storing it server side will result in the same problem. Would appreciate your feedback on that one.
webnoob
@itay, good point i nv thought of that
jiewmeng
@webnoob - if this is an item id I would never bother with encrypting it. Items ids (like here or any other system) are not to be considered secrets. You should always check in the server if user X has permissions on item Y.
Itay Moav
You are misunderstaning what I am saying. I know the server checks for permissions; this is a must. The OP has changed and since been edited but the point it was making was how to know which document is being edited IF someone changes the value in a hidden field and then check permissions for that ID. Encrypting the ID will stop that field from changing into anything other then what you are expecting, ie. you can't just change ID 1 into ID 2 instead and you can rely on the fact that the ID that has been passed through hasn't been tampered with.
webnoob
A: 

It should not be based on anything submitted by the user. You should always check user permissions on server side. An attacker can prepare any request to your server.

Maciej Kucharz
+4  A: 

You must store some kind of id at the client-otherwise how would you know which item to edit?
This does not free you from the mandatory check on the server that the current user has privileges to edit/see the edited item.
Other then that, why would you care how he got to edit the item (whether by lawful use of the web tool, or by editing the hidden/whatever field).

Itay Moav
jiewmeng
it is defined in the php.ini
Itay Moav
Well surely that would depend on which you are actually calling. $_POST or $_GET. You can then choose which one is used and as far as I was aware using global vars in that way isn't a good idea.
webnoob
i think it shld be ok to store the id field in a hidden field as long as i check it. i have Zend_Acl in place. except that i use `$this->_getParam()`, it seems to get params from both GET and POST. and i just tested, when i have different values in GET and POST, i will get from GET. but all said, i think as long as i use the same method of getting the id i shld be safe?
jiewmeng
Using some kind of RESTful framework this problem resolves itself; the ID of the record being edited will be included in the URL. Something like a POST request to /users/123
meagar
+1  A: 

as ppshein said, storing sensitive ids in a hidden var is NOT safe. Would you store a password in a hidden var? Its really easy for even a novice hacker to get that data.

You need to make sure that all access control is enforced by the server.

in your case, you need to make sure that the user who is logged in (the one on the session) is the owner of the profile being edited. Or that the user who is making the edits has permissions to edit that profile (e.g. is an admin)

hvgotcodes
A: 

Agree with all the points above but if you really do need to store something clientside for whatever reason, you can always encrypt the data and decrypt when you need to use it but again, using sessions would be the best way to deal with it as they are not accessible client side.

webnoob
that doesn't change the fact that the user can change the value tho.
jiewmeng
Of course and that is where the server side validation comes in. If a hacker changed a value in an encrypted ID, then it would no longer decrypt correctly and therefore you would know something was wrong.
webnoob
then i think the encryption may not be too useful in this case as the id isnt a secret. encrypt or not, i will still need to check if the user has access to the resource requested.
jiewmeng
also regarding your comment on @ppshein's post, i think i cant rely on a decrypt-able hash as a valid request. if somehow, the user knows your hashing method, he can create valid hashes to use.
jiewmeng
The user wouldn't know. That is the whole point of encryption (not hashing). You have a key stored in script somewhere (or somewhere else) and you use that for the encryption and decryption. You can have different levels of encryption as well (up to 256 bits (maybe more, not sure - never gone higher :)) If you need to show something client side, encryption IS the best way to do it.
webnoob
I know the ID isn't a secret, the point is that you stop the user changing the value. So you know you are checking the permissions on the correct document server side.
webnoob