Re: [PHP] Separation between View and State (The Back Button)

2006-07-13 Thread Richard Lynch
That will work fine.

The other suggestion half-remembered by a previous poster is to do a
header("Location: ") after you process the post, so that their "Back"
button doesn't take them through the POST again.

However, a user who is intentionally playing with the submit, forward,
and back buttons can quickly prove that this is prone to error.

header("Location: ") also comes with a great deal of subtle issues
such as session cookie problems and HTTP connection waste.

I personally prefer the unique token approach.

YMMV

On Thu, July 13, 2006 1:27 pm, Michael B Allen wrote:
> Let's say you have a "Buy" button that posts a form to a script that
> inserts or increments the quantity of a record in a shopping cart
> table. So you click "Buy" and then "Checkout". Now if you hit the Back
> button it asks the user if they would like to repost the form. If you
> click "Ok" the db script runs again and now they have two items in the
> cart. Not good.
>
> It seems to me this is a fundamental model view controller kind of
> problem. There's no seperation between the view and the controller.
>
> What I'm thinking is that I need to give each form a unique token.
> When
> the form is submitted a new token is generate. So if at any time a
> form
> is reposted the token will be invalid and action regarding the form
> contents can be igored.
>
> Specifically I'm thinking of somthing like:
>
>  function token_generate() {
> return $_SESSION['state_token'] = rand(1,9);
> }
> function token_matches() {
> return isset($_POST['t']) && $_SESSION['state_token'] ==
> $_POST['t'];
> }
>   if (token_matches()) {
>   // insert or update cart contents
>   }
> ?>
>
> Shopping Cart
>
> 
>echo " . "\"/>\n";
> ?>
>
> // display cart contents
>
> I don't get to do much web programming so I'm wondering what the PHP
> crowd thinks of this method. Can anyone improve on this? Is it fatally
> flawed? How would you solve this problem in general?
>
> Thanks,
> Mike
>
> --
> Michael B Allen
> PHP Extension for SSO w/ Windows Group Authorization
> http://www.ioplex.com/
>
> --
> PHP General Mailing List (http://www.php.net/)
> To unsubscribe, visit: http://www.php.net/unsub.php
>
>


-- 
Like Music?
http://l-i-e.com/artists.htm

-- 
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Separation between View and State (The Back Button)

2006-07-13 Thread Paul Novitski

At 11:27 AM 7/13/2006, Michael B Allen wrote:

Let's say you have a "Buy" button that posts a form to a script that
inserts or increments the quantity of a record in a shopping cart
table. So you click "Buy" and then "Checkout". Now if you hit the Back
button it asks the user if they would like to repost the form. If you
click "Ok" the db script runs again and now they have two items in the
cart. Not good.

It seems to me this is a fundamental model view controller kind of
problem. There's no seperation between the view and the controller.

What I'm thinking is that I need to give each form a unique token. When
the form is submitted a new token is generate. So if at any time a form
is reposted the token will be invalid and action regarding the form
contents can be igored.



Perhaps, but I'll bet that a lot of re-posts will be from people who 
click, realize they forgot to change the quantity or another value, 
and back up in order to correct their mistake.  You might consider 
accepting the most recent post, not the first, when the form token 
matches.  You might also want to include a current timestamp in the 
form so that you can easily detect the sequence of multiple posts.


One technique that might help is to insert a processing script 
between input form & output page.  The form posts to the script which 
doesn't download anything to the browser but instead redirects to the 
destination page, so backing up from the destination doesn't 
automatically prompt for a re-post; the user would actually have to 
return to the form and re-submit it manually.  And of course that's 
going to happen, too, so your underlying engine will need to be smart 
enough to know how to deal with multiple buy requests for the same 
product in any case.


Regards,
Paul 


--
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Separation between View and State (The Back Button)

2006-07-13 Thread Michael B Allen
On Thu, 13 Jul 2006 14:41:21 -0400
Jim Moseby <[EMAIL PROTECTED]> wrote:

> > 
> > Let's say you have a "Buy" button that posts a form to a script that
> > inserts or increments the quantity of a record in a shopping cart
> > table. So you click "Buy" and then "Checkout". Now if you hit the Back
> > button it asks the user if they would like to repost the form. If you
> > click "Ok" the db script runs again and now they have two items in the
> > cart. Not good.
> > 
> ::snip::
> 
> Someone posted here an elegant way of handling that, but I can't remember
> who or the specifics of how.  But, IIRC, it involved a header you can send
> that keeps the page from being included in the browser history.  So when the
> user hits 'Back', it skips the processing page and takes them back to the
> form page.

Actually what would be even better is if there were a header that
indicated the form data should NOT be reposted on back or reload. Anyone
heard of such a thing?

Mike

-- 
Michael B Allen
PHP Extension for SSO w/ Windows Group Authorization
http://www.ioplex.com/

-- 
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



Re: [PHP] Separation between View and State (The Back Button)

2006-07-13 Thread Jochem Maas
Michael B Allen wrote:
> Let's say you have a "Buy" button that posts a form to a script that
> inserts or increments the quantity of a record in a shopping cart
> table. So you click "Buy" and then "Checkout". Now if you hit the Back
> button it asks the user if they would like to repost the form. If you
> click "Ok" the db script runs again and now they have two items in the
> cart. Not good.
> 
> It seems to me this is a fundamental model view controller kind of
> problem. There's no seperation between the view and the controller.
> 
> What I'm thinking is that I need to give each form a unique token. When
> the form is submitted a new token is generate. So if at any time a form
> is reposted the token will be invalid and action regarding the form
> contents can be igored.
> 
> Specifically I'm thinking of somthing like:
> 
>  function token_generate() {
> return $_SESSION['state_token'] = rand(1,9);
> }
> function token_matches() {
> return isset($_POST['t']) && $_SESSION['state_token'] == $_POST['t'];
> }
>   if (token_matches()) {
>   // insert or update cart contents
>   }
> ?>   
> 
> Shopping Cart
>  
> 
>echo " "\"/>\n";
> ?>
> 
> // display cart contents
> 
> I don't get to do much web programming so I'm wondering what the PHP
> crowd thinks of this method. Can anyone improve on this? Is it fatally
> flawed? How would you solve this problem in general?

this is pretty much *the* way to tackle this issue. plenty of [minor] variations
of your basic concept have been proposed as a solution to the back button 
problem
on this list... the most notable difference being increased randomness in the 
token
and keeping an array of valid tokens (e.g. how many forms will a user request 
before
post'ing one of them?) and binding a given token to a given form (and/or data 
input 'type')

> 
> Thanks,
> Mike
> 

-- 
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php



RE: [PHP] Separation between View and State (The Back Button)

2006-07-13 Thread Jim Moseby
> 
> Let's say you have a "Buy" button that posts a form to a script that
> inserts or increments the quantity of a record in a shopping cart
> table. So you click "Buy" and then "Checkout". Now if you hit the Back
> button it asks the user if they would like to repost the form. If you
> click "Ok" the db script runs again and now they have two items in the
> cart. Not good.
> 
::snip::

Someone posted here an elegant way of handling that, but I can't remember
who or the specifics of how.  But, IIRC, it involved a header you can send
that keeps the page from being included in the browser history.  So when the
user hits 'Back', it skips the processing page and takes them back to the
form page.

Maybe a quick STFA will turn up something.

JM

-- 
PHP General Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php