The Joomla! Forum ™





Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 11 posts ] 
Author Message
PostPosted: Sat Oct 22, 2005 9:21 pm 
User avatar
Joomla! Explorer
Joomla! Explorer

Joined: Thu Oct 06, 2005 6:33 pm
Posts: 455
Location: Lugano - CH
My component have few form fields. After user click Submit, all values go into DB and are displayed on the next screen.
If in this screen user press F5 (refresh) all variables are submited twice. And so on..

How to disable this?


Top
 Profile  
 
PostPosted: Sun Oct 23, 2005 8:02 am 
User avatar
Joomla! Guru
Joomla! Guru

Joined: Thu Aug 18, 2005 8:53 am
Posts: 831
Location: Switzerland
One way is that the page getting the POST treats the submission, then redirects to another page without POSTs. If the user hits F5, he will get the redirected page, and no double posts.

Another obvious way is to check for double submissions before updating DB ;)

Normally, good browsers ask before re-submitting...

_________________
Beat 8)
www.joomlapolis.com <= Community Builder + CBSubs Joomla membership payment system - team
hosting.joomlapolis.com <= Joomla! Hosting, by the CB Team


Top
 Profile  
 
PostPosted: Sun Oct 23, 2005 2:41 pm 
User avatar
Joomla! Explorer
Joomla! Explorer

Joined: Thu Oct 06, 2005 6:33 pm
Posts: 455
Location: Lugano - CH
Ok, I think I solved the problem.

I have task=addtocart, and task=viewcart

When user submit some entry, then I do 'addtochart' and in the same function instead of calling viewCart() function I do mosRedirect("index.php?task=viewcart..."). If user press F5 notthing's happen, only refresh a cart content.

Thanks for idea.


Top
 Profile  
 
PostPosted: Fri Nov 04, 2005 1:00 am 
Joomla! Fledgling
Joomla! Fledgling

Joined: Fri Nov 04, 2005 12:50 am
Posts: 4
But don't you have the same problem now, except that this time it's the back-button that creates the duplicate entry???

In my opinion it is indeed best to check for doubles while writing the data.... after all, with a refresh the data is exactly the same as the post from the previous page....


Even better, if you are using php, use session vars...


Start a session and put this on top of your form:

$_SESSION['refresh'] = false;

at the bottem of your script that handles the data-capture put:

$_SESSION['refresh'] = true;

now, before you enter the data in your database, test on this:

if (!$_SESSION['refresh'])
{
//enter the data in your dbase
} else {
//do something else
}

full proof sollution !!!

cheers ;-)


Last edited by TVScoundrel on Fri Nov 04, 2005 1:03 am, edited 1 time in total.

Top
 Profile  
 
PostPosted: Fri Nov 04, 2005 9:20 pm 
User avatar
Joomla! Explorer
Joomla! Explorer

Joined: Thu Oct 06, 2005 6:33 pm
Posts: 455
Location: Lugano - CH
No I don't have that problem :)

page1 -> POST all data to page2.
paage2 do some database update or insert and without showing anything do mosRedirect(page3);
Page3 shows data
For user and browser there are only 2 pages : page1 and page3
So, back button goes to the page1 and forward after that to the page3.

this work without session and without double data, and double-data-checking :)


Last edited by misk0 on Fri Nov 04, 2005 9:22 pm, edited 1 time in total.

Top
 Profile  
 
PostPosted: Fri Nov 04, 2005 10:21 pm 
Joomla! Fledgling
Joomla! Fledgling

Joined: Fri Nov 04, 2005 12:50 am
Posts: 4
True, but in my example you don't need the double-data-checking either.
You should allways check for doubles if you want to do efficient data-capturing.

With messages for a guestbook you won't have that problem, but supose you have a
web interface to handle the contacts for your business, checking on existing addresses... etc...

Anyhow, either solution works, it's a programmer choice...  ???

I use one bool session var and because of that, I can handle all data processing on only one page
without ever risking a refresh double.

For big projects this realy pays off; you only need to keep track of one page to take care of both
getting the data from the user, submitting the form to itself and then handling the posted data.

:)

Another advantage of this method is that it enables you to actually "handle" a refresh.
The webpage knows it is being refreshed and can reply accordingly. So the complete
action is under 'your' controle. And that's exactly what you usualy would want  ;)


Last edited by TVScoundrel on Fri Nov 04, 2005 10:27 pm, edited 1 time in total.

Top
 Profile  
 
PostPosted: Fri Nov 04, 2005 10:58 pm 
User avatar
Joomla! Explorer
Joomla! Explorer

Joined: Thu Oct 06, 2005 6:33 pm
Posts: 455
Location: Lugano - CH
Here is an situation a little bit different. I;m adding product to my web shopping cart. So, if user click Refresh, he will add same product with dobule quantity, which is not an error, but I want to avoid this.
I have a table with products and when user try to add new product, first I check if there is a same product. If it is then I just add a quantity of new to old. If there is no I add that product to the cart.
So, there are no unique data of one product in this table, and I don't need them :)
IMHO refresh is bad thing in web apps, and I don;t need to know when have user refreshed page :)

Before Joomla, in my old app I used your way to contorol post/get data flow, and it was working.
I;m not even sure you can write to session under Joomla. Did you tried?


Top
 Profile  
 
PostPosted: Wed Nov 30, 2005 4:21 am 
Joomla! Fledgling
Joomla! Fledgling

Joined: Wed Nov 30, 2005 4:18 am
Posts: 2
TVScoundrel wrote:
But don't you have the same problem now, except that this time it's the back-button that creates the duplicate entry???

In my opinion it is indeed best to check for doubles while writing the data.... after all, with a refresh the data is exactly the same as the post from the previous page....


Even better, if you are using php, use session vars...


Start a session and put this on top of your form:

$_SESSION['refresh'] = false;

at the bottem of your script that handles the data-capture put:

$_SESSION['refresh'] = true;

now, before you enter the data in your database, test on this:

if (!$_SESSION['refresh'])
{
//enter the data in your dbase
} else {
//do something else
}

full proof sollution !!!

cheers ;-)

I registered just to tell you that your idea is a terrible idea, because the user wouldn't be able to add another item to their cart, after that code.


Top
 Profile  
 
PostPosted: Wed Nov 30, 2005 11:57 am 
Joomla! Fledgling
Joomla! Fledgling

Joined: Fri Nov 04, 2005 12:50 am
Posts: 4
That is just plain NOT true; on top of the form the $_SESSION['refresh'] gets the value false... so adding another item is no problem.

(May be nice to read the whole thing before replying noncense!)


Top
 Profile  
 
PostPosted: Thu Dec 01, 2005 4:49 am 
Joomla! Fledgling
Joomla! Fledgling

Joined: Wed Nov 30, 2005 4:18 am
Posts: 2
TVScoundrel wrote:
That is just plain NOT true; on top of the form the $_SESSION['refresh'] gets the value false... so adding another item is no problem.

(May be nice to read the whole thing before replying noncense!)

Ok, first of all, I read the whole thing. Reseting the session variable when the page loads wouldn't work, because when you refresh the page you are reloading it. Trust me, I am not stupid, and I do not make comments against some's code without testing it first.

Incase you do not realize, your code is working like this...
1) Declaring session var false.
2) Checking is session var is flase, and if so executing the code.
3) Declaring session var true.

When you refresh the page it is doing the same exact thing over again, firstly declaring the var as false.
Your code is correct, I'll give you that, but is a n00b used this code he/she would not be able to figure it out, because in order to get this to work, you cannot declare the session var as false.

Below is an example of your code that I was able to get to work:
Code:
<?php
session_start();

if ($mode == "submit")
{
   if (!$_SESSION['post'])
   {
      (code to enter data into database)

      echo "<meta http-equiv=\"refresh\" content=\"3; url=http://someurl.com\">";

      $_SESSION['post'] = true;
   }
   else if ($_SESSION['post'])
   {
      $page_error = "Post already submitted.";
   }
   else
   {
      $page_error = "Session variables corrupted!";
   }
}
else
{
   $_SESSION['post'] = false;

   echo "
      <form action=\"" . $_SERVER['PHP_SELF'] . "?&mode=submit\" method=\"post\">
         <label for=\"TITLE\">Title for post: </label><input name=\"TITLE\" size=\"30\" type=\"text\" /><br />
         <label for=\"USER\">Desired username: </label><input name=\"USER\" size=\"30\" type=\"text\" /><br />
         <label for=\"TEXT\">Text for post: </label><br />
         <textarea cols=\"60\" name=\"TEXT\" rows=\"20\"></textarea><br />
         <input name=\"SUBMIT\" type=\"submit\" value=\"Submit\" />
      </form>
   ";
}
?>


You must also have the "session_start()" function declared on the page it is redirecting to.

I am sorry if I came off sounding like your code was completely incorrect, but I just wanted to point out that it is not a good idea to use it the way you did. I am also sorry if I just misunderstood the way your code was meant to be used.


Last edited by Frosty_Tigger on Thu Dec 01, 2005 4:51 am, edited 1 time in total.

Top
 Profile  
 
PostPosted: Thu Dec 01, 2005 7:48 pm 
Joomla! Fledgling
Joomla! Fledgling

Joined: Fri Nov 04, 2005 12:50 am
Posts: 4
No offence taken, but maybe I was incomplete...

The problem was not with posting to the same page: $_SERVER['PHP_SELF'],
but to a second page without having to use the meta refresh to yet a third page.

Later on I indeed pointed out that you could use this to post to the same page, but I didn't specify how,
so here it comes  ;)

a link on the webpage index.php says "click here to add item" and points to

index.php?action=newitem

index.php states:

Code:
<?php
session_start();

$action = htmlspecialchars($_GET['action']);

if ($action == 'newitem')
{
 require_once('html/newitemform.html');
 $_SESSION['refresh'] = false;
}

if ($action == 'additem')
{
 if (!$_SESSION['refresh'])
 {
  require_once('includes/additem.php');
  $_SESSION['refresh'] = true;
 } else {
  [handle the refresh]
 }
}
?>



now the action of the form states: $_SERVER['PHP_SELF'] . "?action=additem"
or you can put it in a hidden form component, but then you need to $_POST['action']
as-well, first making sure it didn't get any data from $_GET...

I hope this will make you change your mind, as I said before, it is only a bool... The smallest var available, yet it allows for detecting a refresh and handling it [in stead of preventing it with a meta refresh which I believe takes extra time on slow connections.(but I'm not sure about that :))]

Ofcourse if you wish to view an empty form again after the submit I'm afraid you have no other option but to use
a meta refresh. But in most cases you don't need to go back to the form.

Anyway, your solutions is about the same isn't it ;)


If anyone wonders "why the htmlspecialchars()"
it is to prevent hackers to insert scripts into your programs via the URL.

cheers.


Last edited by TVScoundrel on Thu Dec 01, 2005 8:46 pm, edited 1 time in total.

Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 11 posts ] 



Who is online

Users browsing this forum: No registered users and 2 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Jump to:  
Powered by phpBB® Forum Software © phpBB Group