Solved

PHP: reload page adds quantity to cart

Posted on 2011-09-29
8
365 Views
Last Modified: 2012-05-12
I am an experienced .NET programmer learning PHP. The project I'm working on is a pizza shop menu where the user can create a custom pizza & add it to the cart.  

When the user clicks the Add to Cart button, which is on the menu page, the add_item function is called & one new item is added to the cart. The user is redirected to the cart page, using the include function.

include('cart_view.php');

At this point, if the user reloads the page (F5), the quantity of the item is increased by one. The browsers even warn about this. I've searched the Internet & I believe the header function is the solution, but I don't know where to place it or what to check for, to make it work.

header('Location: cart_view.php');

If I put it after the add_item function, (where the include function currently is) the cart page displays, but with zero items in the cart. But if you go back to the menu page & click on the cart button, which calls the show_cart function, the items are in the cart.

Thanks in advance for any help or suggestions.
0
Comment
Question by:LezlyPrime
  • 2
  • 2
  • 2
  • +2
8 Comments
 
LVL 21

Expert Comment

by:Kim Walker
Comment Utility
I'm not getting the picture here. When the user clicks the Add to Cart button, I'm assuming a form is being submitted or some javascript is being executed which sends the pizza configuration to a PHP page which returns a page with the cart contents. How is the pizza configuration being passed to the cart? If you are using a query string or form to send the configuration, refreshing the page will resend the query string or form and would indeed add another pizza. Can you be more specific?
0
 
LVL 82

Accepted Solution

by:
Dave Baldwin earned 250 total points
Comment Utility
On the shopping cart software I'm responsible for, the 'add to cart' is in a PHP file that does not display HTML.  It ends with a header redirect to another page that queries the database for the current contents of the cart and displays it.  The page that actually displays Only does a query for contents and does not add anything so you can refresh it all you want.
0
 
LVL 21

Expert Comment

by:Kim Walker
Comment Utility
I'll have to look into this further tomorrow unless another expert is able to comment sooner. But I think the problem is in the include method. It doesn't redirect. It's more of an insert. It embeds the contents of the other file in the current file. This much I'm sure of. When I need to redirect, I usually return an HTML shell page with a refresh meta tag. But there may be a better way.
0
 
LVL 108

Expert Comment

by:Ray Paseur
Comment Utility
Buy these books.  It will help a lot with the ways of thinking that PHP programmers use.  Your experience will enable you to read these and make progress very quickly.
http://www.sitepoint.com/books/phpmysql4/
http://www.amazon.com/PHP-5-Practice-Elliott-White/dp/0672328887

A teaching example of the solution to prevent multiple submits of the same data is shown in the code snippet.  You can copy it and install it on your own machines, or test it on my server here.
http://www.laprbass.com/RAY_multi_submit.php

Best of luck with your studies, ~Ray
<?php // RAY_multi_submit.php
error_reporting(E_ALL);


// PREVENT MULTIPLE SUBMISSIONS DUE TO REPEATED REFRESH, CLICKS ON SUBMIT BUTTON OR FIRING THE BACK BUTTON
// EXAMPLE:
//    if ( multi_submit() )
//    {
//       handle error
//    }
//    else
//    {
//       normal processing
//    }


// ALWAYS START THE PHP SESSION ON EVERY PAGE
session_start();



// A FUNCTION TO RETURN TRUE OR FALSE ABOUT MULTI-SUBMIT CONDITIONS
function multi_submit($type="POST")
{
    // MAKE THE FUNCTION WORK FOR EITHER GET OR POST SUBMITS
    $input_array = (strtoupper($type) == "GET") ? $_GET : $_POST;

    // GATHER THE CONTENTS OF ALL THE SUBMITTED FIELDS AND MAKE A MESSAGE DIGEST
    $string = NULL;
    foreach ($input_array as $val)
    {
        // CONCATENATE ALL SUBMITTED VALUES
        $string .= $val;
    }
    $string = md5($string);

    // IF THE SESSION VARIABLE IS NOT SET THIS IS NOT A MULTI-SUBMIT
    if (!isset($_SESSION["_multi_submit"]))
    {
        // SAVE THE SUBMITTED DATA MESSAGE DIGEST
        $_SESSION['_multi_submit'] = $string;
        return FALSE;
    }

    // IF THE SESSION DATA MATCHES THE MESSAGE DIGEST THIS IS A MULTI-SUBMIT
    if ($_SESSION['_multi_submit'] === $string)
    {
        return TRUE;
    }
    else
    {
        // SAVE THE MESSAGE DIGEST TO DETECT FUTURE MULTI-SUBMIT
        $_SESSION['_multi_submit'] = $string;
        return FALSE;
    }
}



// SHOW HOW THIS IS DONE
if (!empty($_POST))
{
    if (multi_submit())
    {
        die("ALREADY GOT THAT");
    }
}



// CREATE THE FORM FOR THE DEMONSTRATION
$form = <<<FORM
<form method="post">
ENTER SOMETHING, THEN REENTER IT
<input name="foo" />
<input type="submit">
</form>
FORM;

echo $form;

Open in new window

0
How to improve team productivity

Quip adds documents, spreadsheets, and tasklists to your Slack experience
- Elevate ideas to Quip docs
- Share Quip docs in Slack
- Get notified of changes to your docs
- Available on iOS/Android/Desktop/Web
- Online/Offline

 
LVL 2

Expert Comment

by:maricksville
Comment Utility
Consider @DaveBaldwins post above. It seems like youre faced with a design issue, in that the way the process is designed is causing the problem. If you modify the design you should overcome the problem.

At the moment the design process seems to run this course

1.User clicks add pizza button
2. Re-direct or include the 'cart' page and add one pizza.

From Daves comment you could change the process to something more like this:

1. User clicks add pizza button
2. Send data to a standalone script and add the pizza
3. If adding the pizza was successful NOW re-direct to a cart page.

You can then refresh the cart page and you wont add anything as the data was added on the standalone script page. This is a failry simple re-design. The event that send data to the cart page now sends data to your standalone script. The function that adds the data on your current cart page is now moved to the standalone script. If the script is successful now re-direct using the header() function to your cart page.

Hope that helps.
0
 
LVL 108

Expert Comment

by:Ray Paseur
Comment Utility
Agree that it is something of a design problem.  Message digests can help reduce the risk of accidental duplicate submissions.  You are not limited to the use of the multi-submit() function I showed above; you can use the md5() function in all sorts of creative ways.  You might put it into a column of a data base table and let it carry the md5() encoding of the INSERT query.  If you had a UNIQUE index over the md5 column and the current time, (perhaps accurate to the minute) you could catch MySQLl_ErrNo() #1062 and reject duplicate attempts to insert the same information into the table.  Or you could make an md5() string from the IP address, the value of time() (perhaps to the minute or 5-minute interval, whatever you wanted) and the order details.  You might also use a session counter or some other method of detecting the path through the site.  Most PHP installations set HTTP_REFERER correctly.
0
 

Author Comment

by:LezlyPrime
Comment Utility
Thanks for all the great input & ideas to try. I'll be working on it this weekend.

~later
0
 

Author Closing Comment

by:LezlyPrime
Comment Utility
So it took some tinkering, but I got it to work. It was a basic design problem. You all had good input, but Dave Baldwin nailed it first with a suggestion for a different approach that worked, so I'm awarding him the points. I hope that is acceptable.

I appreciate everyone's input. Ray, I'll be looking more closely at the alreadyGotThat code you posted & also more about message digests. Thanks!
0

Featured Post

What Security Threats Are You Missing?

Enhance your security with threat intelligence from the web. Get trending threat insights on hackers, exploits, and suspicious IP addresses delivered to your inbox with our free Cyber Daily.

Join & Write a Comment

Nothing in an HTTP request can be trusted, including HTTP headers and form data.  A form token is a tool that can be used to guard against request forgeries (CSRF).  This article shows an improved approach to form tokens, making it more difficult to…
Since pre-biblical times, humans have sought ways to keep secrets, and share the secrets selectively.  This article explores the ways PHP can be used to hide and encrypt information.
Learn how to match and substitute tagged data using PHP regular expressions. Demonstrated on Windows 7, but also applies to other operating systems. Demonstrated technique applies to PHP (all versions) and Firefox, but very similar techniques will w…
The viewer will learn how to look for a specific file type in a local or remote server directory using PHP.

771 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

12 Experts available now in Live!

Get 1:1 Help Now