Using the jQuery autosave plugin
This article was originally written in 2011 in response to queries about a plugin hosted on the jQuery site, originally written by Raymond Julin. The plugin has subsequently been removed from jQuery and the source code has not been updated since 2010. This article provides an explanation on its usage, and has applied a number of fixes to the original code.
Let’s start with the form – I’m using php to retrieve data from a database and display it in a form for editing. To make the demo worthwhile I’ve added various input elements:
<form action="autosave7.php" method="post"> <fieldset> <label for="name">Name:<input type="text" name="name" id="name" value="<?php echo $row['name'] ?>"/></label> <label for="email">Email:<input type="text" name="email" id="email" value="<?php echo $row['email'] ?>" /></label> <label for="textboxarea">Text:<textarea id="textboxarea" name="textboxarea" rows="2" cols="20"><?php echo $row['textarea'] ?></textarea></label> <label for="selectfield">Select:<select id="selectfield" name="selectfield"> <option>Option 1</option> <option>Option 2</option> </select></label> <label for="radio1">Radio 1:<input type="radio" name="radios" id="radio1" value="radio1" <?php if ($row['radio']=="radio1") echo "checked='checked'"; ?> /></label> <label for="radio2">Radio 2:<input type="radio" name="radios" id="radio2" value="radio2" <?php if ($row['radio']=="radio2") echo "checked='checked'"; ?> /></label> <label for="checkvalue">Check with value attribute:<input type="checkbox" name="checkvalue" id="checkvalue" value="sbtest" <?php if ($row['checkboxvalue'] ) echo "checked='checked'"; ?>/></label> <label for="check">Check with no value attribute:<input type="checkbox" name="check" id="check" <?php if ($row['checkbox']==1 || $row['checkbox']=='on') echo "checked='checked'"; ?>/></label> <input type="hidden" name="id" value="<?php echo $row['id'] ?>" /> <input type="submit" value="Save changes" /> </fieldset> </form> <p id="message"></p>
I’m including an empty element for the message, just to keep the javascript simple – a more sophisticated solution would append this when required. Now, to add the autosave functionality I need to include this javascript:
$("input,select,textarea").autosave({ url: "autosave7.php",//set the php file that updates the database method: "post", grouped: true,//send data for all fields with the autosave success: function(data) {//on a successful update... $("#message").html("Data updated successfully").show();//...show a message... setTimeout('fadeMessage()',1500);//...and then fade it out after an interval }, send: function(){//on a save... $("#message").html("Sending data....");//..show a message }, dataType: "html" }); function fadeMessage(){ $('#message').fadeOut('slow');//just a function to fade out the message }
All this just leaves the php to update the database, which is:
if ($_POST['checkvalue']!='false') $checkvalue = $_POST['checkvalue']; else $checkvalue = 0;//checkbox with a value attribute if ($_POST['check']=="true" || $_POST['check']=="on" || $_POST['check']=="checked" ) $check = 1; else $check = 0;//and one without $qstring="UPDATE test_autosave SET name = '".$_POST["name"]."' ,"; $qstring .= " email = '".$_POST["email"]."',"; $qstring .= " textarea = '".$_POST["textboxarea"]."',"; $qstring .= " selectfield = '".$_POST["selectfield"]."',"; $qstring .= " checkbox = ".$check.","; $qstring .= " radio = '".$_POST["radios"]."',"; $qstring .= " checkbox = '".$check."',"; $qstring .= " checkboxvalue = '".$checkvalue."'"; $qstring .= " WHERE id =".$_POST['id'].""; mysql_query($qstring);
Because jQuery 1.6 changed the way form elements are posted by the autosave plugins, the autosave plugin itself will not work correctly with this and later versions of jQuery where radio buttons are used. A small change is needed to the plugin to cope with this – you can download the amended version here: jQuery autosave plugin
Inevitably, there’s a working demo here – just to make it more obvious the demo includes a snapshot of the database itself to show the updates.
A few people have asked for copies of the php files used in the demo – so here they are as text files:
- Demo page code: autosave_demo5.php
- Database update code: autosave7.php
- Code that updates the page via ajax: autosave6.php
Updated 07/05/2014 to cope with value attributes on checkbox fields
Tags: jQuery
Hi Simon, everything is OK, but when you select grouped:false radio and checkbox not working.
So here is solution for:
if (options.grouped) {
nodes.each(function (i) {
/**
* Do not include button and input:submit as nodes to
* send, EXCEPT if the button/submit was the explicit
* target, aka it was clicked
*/
if (!$(this).is(‘button,:submit’) || e.currentTarget == this) {
if ($(this).is(‘:radio’) && $(this).prop(‘checked’)==false)
return;
vals[this.name] = $(this).is(‘:checkbox’) ? //if it’s a checkbox…
$(this).prop(‘checked’) ? $(this).val() != ‘on’ ? $(this).val(): true : //and it’s checked, if the checkbox has a value (not just ‘on’, return this, otherwise just a boolean true
false : //if it’s a checkbox and not checked, return false
$(this).val();//and if it’s not a checkbox, return the value
}
});
}
else {
if ($(this).is(‘:radio’) && $(this).prop(‘checked’)==false)
return;
vals[actsOn.name] = $(actsOn).is(‘:checkbox’) ? //if it’s a checkbox…
$(actsOn).prop(‘checked’) ? $(actsOn).val() != ‘on’ ? $(actsOn).val(): true : //and it’s checked, if the checkbox has a value (not just ‘on’, return this, otherwise just a boolean true
false : //if it’s a checkbox and not checked, return false
$(actsOn).val();//and if it’s not a checkbox, return the value
}
I don’t think there’s an issue with multiple forms – you just need to make sure the autosave calls appropriate code. See this demo which has two forms updating the same database table via two different update scripts.
Hi Simon thanks for the code. It works fine when there is only one record. However in about half the records have two records. This then loops through and creates two forms on the same page. When this happens the autosave only works for the second form
How do I create two instances of the script or what do I need to rename dynamically in the script that will enable the autosave to work on both forms?
(I am very much not a newbie with jquery and javascript by the way)
Louis, changing grouped to false works fine for me – I can see just the changed element being posted using the console. Are you sure that your target php file copes with just a single value being posted? Mine would need some amendment to handle this.
Simon, one more try at this. I would like to use the grouped: false method and cannot get checkboxes to work using this method. They work fine with grouped: true. I know your demo uses grouped: true and works, can you try it using ‘false’. I have some very large forms, I would rather not have to do massive SQL updates when only one tiny piece of data is changed. Grouped:false checkboxes would be ideal.Thanks.
The demo works fine for me with textarea. Check the code to see how it’s done.
Simon,
I tried, but it doesn’t work for textarea. Any hint ??
Thanks
Simon,
re: $(“.autosave”).autosave(..);
from back in March.
It took me a while to get back to it but this was just what I needed. Now have complete control for user feedback. Thanks.
It’s impossible to guess why you have a problem. Use the console to help you identify any issues with your js.
Simon
My autosave6.php file is not reload when autosave occurred. Please let me know how i solve this problem
The first thing to try is to uncouple the final submit
input
from autosave(). As it stands it’s going to fire the autosave.As my last response, try making your selector:
Simon, I hate to bother you about this but I still can’t get it to work. It autosaves just fine but I can’t get the submit button to do anything. This is the code I have, http://karenmcook.com/AutosaveCode.txt
Not very clear what your setup is, but you could just exclude the submit button from the autosave javascript. The best way of doing this will depend on your html, but your could, for example, set a class of
autosave
on all of your various field elements and use that as the selector:Alternately, look into the use of the jQuery .not() selector.
Hi Simon,
The autosave works great but I have a question. I am really new to jQuery so I probably need more explanation than others. I have a form that updates 4 tables. I have the auto save working to update these tables but there is one issue that I am having. I have a submit final button where the user can make a final submission and once that is done, no more edits are allowed. When a user submits the final, the submit date is entered into a db table. Right now if I click the submit final button, nothing happens. How do I get the form to allow the user to submit the final form and update the date info into the database?
Are you trying to generate a message from the ajax response? If so you can use the
success
property as described above. If you look at the demo code you’ll see I’m using that to show the updated database snapshot.Hey @simon, its working well. I just want to show “HTTP response status” after submitting the form, where should I add those header?
Thanks in advance.
ok. i create the colum and work fine. thank you
Your table has no field called
checkboxvalue
, but your update SQL is trying to update that field.this is my autosave7.php http://pastebin.com/yajR81T1
and this is the db and table http://prntscr.com/6rniez
The problem is clearly in the update then, as I said. Do you have a database set up called
test_autosave
with the correct fields? Does your script log on to the database successfully? If you run the SQL directly on the database does it update?ok, look http://lipedns.com.br/jq/autosave_demo5.php
i dont include css.
Suggests there’s something wrong with your update script then, but more than that it’s impossible to say.
hello, for me, the script dont update the database. another functions its ok. i’m runing on localhost.
thanks a lot. great tutorial
Yes, just set the autosave on those elements you require – for example by adding a class of
autosave
to your required elements and then using:Sorry Simon but I’m still trying to gain control of the ‘Submit’ button for error checking. Is there a simple way to remove ‘Submit’ from the autosave script but retain all other form fields as autosave. I tried to validate on the form page but that was ignored and the save page is just running on the server. Thanks.
Joel
If you take a look at the demo and view the code snippets attached to this page you should be able to select what you need for your project. Just for the avoidance of doubt, the autosave will only fire when a user leaves the text area, not just when they stop typing.
Have you though about creating a video tutorial?
I’m a bit confused with what I’m missing as I can’t seem to get the autosave to just save the text area, I’ve tried others but they don’t seem to save to database.
What I plan to do is to allow the user to type in the textarea and after they stop typing the autosave does its job.
Currently following your code and making changes I haven’t got to the auto save part working.
Well, this script doesn’t do anything like that. Very simply you could just run a few if statements and check the value of your input fields, and if any of them are blank, provide a message to the user.
I appreciate this script. In order to meet my needs I’m trying to determine the best way to notify the user (only) when Submit is clicked and I determine that certain fields are blank.I currently don’t seem to have that control. Thoughts?
Just set your button to fire a
.change()
on one of the form fields.Hi Simon,
i have a Button which clears some fields in my form:
$(function() {
$(“#dbutton”).click(
function(){
$(‘#datepicker’).val(”);
$(‘#ruhrzeith’).val(”);
$(‘#ruhrzeitm’).val(”);
}
);
});
and it would be perfect if the button starts the “autosave script”. any idea? ๐
Everything alright. the data in my database was saved with UMLAUTE (รผ.ร.ร.) i replaced now every UMLAUT with the right code
thx
I cannot recreate this on my demo. Umlauts save fine using FF. Your code snippet appears to have an additional ‘accept-charset’ argument – is that the issue?
Everything works perfectly except of the special german characters: ร ร ร.
If i turn off the jquery-script and use a simple button to start the php-Script to save, every char will save correctly to the database. but if i turn on the jquery-plugin and the autosave turns on, the charset get loss. It saves strange symbols to the database instead of my chars ร ร ร ๐
[code]
url: “autosave7.php”,//set the php file
accept-charset: “iso-8859-1”, //set charset
method: “post”,
grouped: true, //send data for all fields with the autosave
[/code]
Just set the plugin up to run where you want it by using standard jQuery selectors:
Hi Simon,
i have two forms on one site. And i want that just the first form is autosaved. But if i type something in the second form the script starts too.
How can i edit yout super script ๐ that just one form is autosaved. i have the formโs in different divโs. i hope you understand. my english grammar is not so good ๐
thanks a lot!!
Thanx for your quick reply, Simon! That was just the right hint!
Chees
Mirnow
I can only guess…but it sounds like you might not have the html if your form correct. Check what data is being posted by the plugin by viewing the console window in your browser dev tools.
Hi Simon, thanks for this great work!
Unfortunately I’m running into a problem with an array in my form. It updates/inserts only the last array (id=117) of the form. Independent which value is changed in the form. I’m using this peace of code. Do you see what I’m doing wrong here? Any hint is appreciated…
html form
…
php script
// handover of the arrays
$ids = $_POST[‘id’];
$fids = $_POST[‘fid’];
$values = $_POST[‘value’];
// run the insert/update loop
for ($i = 0; $i <= count($ids); $i++)
{
$id = $ids[$i];
$fid = $fids[$i];
$value = $values[$i];
// define the query
$query="INSERT INTO tbl_values (iid, fid, value) VALUES (".$iid.", ".$fid.", '".$value."') ON DUPLICATE KEY UPDATE value = '".$value."'";
// run the db query
mysql_query($query);
}
You should be able to manage this by ensuring that clicking the submit button does not call the autosave function. Either use
.not()<.code> in your jQuery selector, or explicitly add a class to the other fields and use this as the selector to fire the autosave.
Excellent script and great instruction. Thank you!
Quick question… can the submit button be made to call the PHP file listed in th form method rather than the autosave.php listed in the function? I’d like to have the submit button pass form values to another PHP file rather than the autosave file.
Hi Jeff
I’m not quite sure what you’re asking here. As it stands the plugin passes all the data from the parent form, so the simplest solution to what you need is just to enclose all the fields you need in one form element. If this isn’t possible for whatever reason you could add some hidden input elements which mirror the values of your other fields.
Custom fields.
I want to use autosave in a specific part of interface, but i need to add custom fields shared with other parts of my interface also.
something like that
$(“#div1 input, #div1 select, #div1 textarea”).autosave(
{
url:”autosave7.php”,
method: “post”,
grouped: true,
data:{customField1:Value1,customField2:Value2},
success: function(data){},
send: function(){},
dataType: “html”
});
I’m not familiar with jsp so can’t answer that, I’m afraid.
can these code be done in jsp?
Start by checking your browser console window to see if the data is being posted correctly by the javascript. If it is then that suggests the problem is with your update code. If you get your update code to echo out the SQL then you can view that in the console window as well – as the response to the post.
Autosave2 applied in this way :
But not saved , the database is Interbase . Can you help me, please !
Have you amended jquery.autosave.js? You can download an amended version from the demo page I posted earlier.
Yes. The js code doesn’t work on my local server. Your file is ok but in local, I put your file demo5 on my local server. i don’t understand, it returns true :false.
Hi Aurelien
My suggested amendment to the js does work. There’s a demo here which is set to handle the value of a checkbox, and the code updates the value if the box is checked. Is this not what you’re trying to do?
Great plugin but same problem as Louis. A group of checkboxes with same name :
When POST, name is set to false if one or two checkboxes are checked and true if all are checked. Is it possible to have the values of each checkbox in array ?
Tried the solution from April 1, 2014 at 11:36 am, but it does not work.
Best explanation on the web. Thank you. It worked first time.
You can use the
option to retrieve the triggering element like this:
... send: function(event){ console.log(event);//returns triggering element }....
You could use this to set a class against the triggering element and then use that to append an error message via the
success
option, dependent on the result from your php code.Thank you for doing this, it really filled in the explanation of the plugin. I’m using this with the “grouped” option set to false – sending only the changed item. Is there a good way to identify this changed form element inside of the javascript so that on success/fail I could address a span next to each individual input field? Your “saving…” message does this great, but I would like to make the indicator more local to the form element.
You can amend the plugin code to do what you want. Change this:
to this:
Which will pass the value of the checkbox if it’s set, otherwise false. For a checkbox $(this).val() will always return the value regardless of whether the box is checked.
actually that is not how checkboxes work. they work just like radio buttons. They will submit the “value” associated with each checkbox. If I check Mon-Wed in a series of checkboxes for a week where each checkbox is named the same, the form data will come through as Mon,Tue,Wed for the field “daysoftheweek”. I can code around it by naming each checkbox differently, even though they are actually a group and stored as such.
That’s the way checkboxes work, I’m afraid. You could easily add some code to your PHP process the checkbox in whatever way you need.
The radio buttons submit the actual value of the radio button however the checkboxes only submit true or false. If I have for example, seven checkboxes for the days of the week I would like to name all checkboxes the same and receive the value of each checkbox rather than true false. What would it take to modify the javascript so that the checkboxes submit their value rather than true/false?
I should say first off that it isn’t my plugin, although the original author seems to have disappeared.
The plugin uses javascript, so there’s no harm in adding your validation via this since in the absence of js it won’t work anyway. However, if your PHP script does the validation and produces error messages then you can handle this via the
success
callback function of .autosave().Hi there. Great work with this as it has helped me greatly with a project.
Question however. I have everything working but if the PHP script that has validation rules in place to valid the users input, how would a PHP error message be handled and posted back to the user?
e.g. If a date field was not inputed in the correct format, the PHP script would find this and would normally display an error message. I understand this can be done in JS but cannot always rely on that.
Any ideas would be greatly appreciated. Thank you!
Your posted PHP file doesn’t match the form element names – that’s why it doesn’t work. As my earlier post, if you are entering the form data as
name=data[fieldname]
where fieldname is name, id etc, then the form, regardless of any autosave, will postdata
as an array, which you can read via$_POST['data']
. You can extend this for multiple values by using the formatname=data[recordid][fieldname]
, which will still postdata
as a two dimensional array.Here’s an example using a one dimensional array in the form. View the source.
Your given example suggests you are using
name
andid
as two separate arrays.i’m try and try but i couldn’t do it
could you give me demo example please or link
my modified is :
[code deleted]
Well, setting the table out like that is just css, it won’t affect the javascript at all. Provided you set up the PHP file that the autosave calls, as my previous post, all should be fine.
thanks for your replied
I expect my question was not clear .
First I wolud like to show data in table using array like this photo :
http://i607.photobucket.com/albums/tt156/smart_mody/hghi_zps18397e1e.png
As you see i fetch data and put it in input type text , every row ass record , when i change value in any field it will change auto using the plugin .
I hope you give me help ๐
thanks
If you’re using arrays in your form then the autosave will work in the same way. You will need to amend the PHP script which is called by autosave to reference the posted data. For example, if you are using field names of
data[name], data[selectfield]
instead ofname, selectfield
as above then you’d need something like this in your PHP file:Hi Simon
i tried to use array [] with this plugin but i failed
could you give me an example to how to use array with it please ?
thanks alot ๐
Frank
You do need to have the database set up properly and be connecting to it. You can check whether the page is passing data to your database by viewing the console window in Firebug, Chrome etc. (See here for info on accessing it. Beyond that it’s difficult to suggest what might be wrong without seeing all your code.
Looks like it is working, but only with the id 1 – … is this real?
This suggests that the query in line 13 of that file is not retrieving any results. Do you have a populated database that you are querying?
Ich habe jetzt folgende Scripte:
– autosave2.php
– autosave3.php
– autosave_demo2.php
– jquery.autosave.js
Und die Datenbank –
Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in /www/htdocs/w00b2203/autosafe/autosave3.php on line 15
Ich erhalte diesen Fehler.
May you help me, is there something missing?
Khalil
Not actually my plugin, I’ve just adapted it as the original author seems to have disappeared. I’m not sure I quite understand your issue – a checkbox can only have two values – on/off. How are you storing your extra data?
Wonderful extension. BUT I am stuck on one issue… checkbox value. As I have a very complex form and i store all checkbox values in one field. Whereas this extension only allows to get 1 or 0.
Is there any way to get value of checked one. If yes then which Jquery version should i use as currently i am using 1.8.0
Thanks in advance.
Yes, you could do this, the plugin should be fine.
Simon: Thanks for the tutorial, really helped me! Curious.. might it be possible to implement the same saving functionality however by using an array list? For example, multiple name[], email[] etc.?
Thanks!
As it stands, the code itself (it’s not mine), doesn’t support this. An approach might be to write a separate routine targetting the textarea you want, and just firing the change event for the element, then outputting the time as well.
See comment 6 above for a similar answer.
You code works really great! I have a request. I would like to know if possible to autosave the textarea after an inveral of every 2 minutes and diplay the atuosave time below the textarea.
thanks for the code.
The plugin works by posting the form as an ajax call, so the data posted is exactly the same as it would be if the form was submitted ‘normally’. Consequently, the posted fields are referenced by their names, dynamically generated or not, so you can build the logic that decides which database tables should be updated in your back end PHP script (or whatever).
Is there a way to pass a querystring or know which control was changed by id? the problem I am having is the page with autosave has a lot of textareas all with different dynamic names and ids so I would like to know which was changed in the autosave page so that I can update the database with a query.
Thanks Simon! Awesome tutorial; helped me tons!
Here you go:
Could you provide a dump of the SQL table? I’m having trouble setting up the SQL tables to match your example. He’s the SQL Query I’m trying to use, but it doesn’t seem to be working with your example:
DROP TABLE IF EXISTS `test_autosave`;
CREATE TABLE IF NOT EXISTS `test_autosave` (
`id` varchar(32) NOT NULL,
`name` text NOT NULL,
`email` text NOT NULL,
`textarea` varchar(255) NOT NULL default ”,
`checkbox` text NOT NULL,
`selectfield` text NOT NULL,
`radio` text NOT NULL
`timestamp` timestamp NOT NULL default CURRENT_TIMESTAMP on update CURRENT_TIMESTAMP,
) ENGINE=MyISAM DEFAULT CHARSET=utf8;
Best way to debug this is to view the console in Firebug, Dragonfly or Chrome, and see what data is being passed and what’s coming back.
Cant make this work? just the onclick wont save it to db
Bear in mind this is not my plugin…
The simplest solution I think would be just not to attach the autosave to your submit button, then the default behaviour will apply.
Hi Simon,
The autosave works for me. However, I would like the submit click button to work by its default behavior by submitting the form to the action page. I am trying to submit the page to the shopping cart so the final data gets saved and the customer is shown the order-thank-you.asp page.
How to I re-enable the event.preventdefault() ?
I will appreciate your input.
JB
You’re right, looks like something has changed between jQuery 1.8.3 and 1.9 – this needed another tweak to the plugin itself, which I’ve now done. You can download the tweaked version here.
Dear Simon,
that’s a nice example and exactly what I was looking for.
Only issue is that checkbox is always set at 0, even if it’s checked.
I’ve tried using your code and checked the plugin, but it doesn’t work.
If I remove the script, and echo in php the value of the checkbox, it is set to “on”, not on true nor checked…
I’m using last version of jquery.
Ever heard of that issue ?
Thanks a lot for your help
Steve
I don’t see the benefit in this since the plugin will autosave anyway whenever a change is made, but you could do this by by forcing the plugin to fire with a simple setInterval():
setInterval(function(){autosave()},2000);//amend interval to whatever you want function autosave(){ $('#name').change(); }
I want to be able to auto save all form fields every 30 seconds.
Can this be done??
Kunal
I’ve updated my example to include a textarea. Make sure you add the textarea to the autosave method.
Hi Simon,
Nice article ๐ but seems like this is not working on my textarea field. Can you enlight me up on it?
I’ve added the files as text links above in case anyone else finds them useful.
Hi Simon,
very interesting article about this autosave plugin.
I tried to make it work and also copied your sourcecode, but somehow it doesn’t work here.
maybe you can send me the (code of the) autosave2.php and autosave3.php files you use (in the demo) for me to resemble the syntax of the files and get it working finally!
I would really appreciate your help and thank you in advance,
Oliver