jQuery Rails Functions

Hi,

I was wondering if anybody who used jQuery with rails could help me
out. I have a droppable that fires a simple function, shown below:

$("#list").droppable({
  accept: ".item",
  hoverClass: 'droppable-hover',
  drop: function(ev, ui) {
    $(this).append("<br>Dropped!");
  }
});

But how could I get this to fire a Rails funciton in the controller so
that the dropped item could be changed at a database level? For
example, when it is dropped, how would I change the updated_at value
to Time.now?

Thanks,

DAZ

Hi,

You need to call a function in your drop handler that goes out to rails to
make the changes.

We do the following in some of our jquery handlers:

var c = {};
c['authenticity_token'] = encodeURIComponent(window._token);
c['user_id'] = <%= current_user.id %>;
$.post("<%= url_for(:action => 'lock', :id => @current_page.form_data.id)
%>", c);

Cheers
Simon

Thanks Simon, but I'm really new to jQuery - I think I know how to
call a function from the drop handler:

$("#dropper").droppable({
  accept: "#dragger",
  drop: dropped()

});

function dropped(){
// do stuff
}

But what do I have to put in the dropped function that actually
accesses rails? You seem to be using $.post, but I don't really know
how this works. Also, I've seen other examples use $.load, and again,
I don't quite get how it works.

Is there any good documentation on this?

cheers again,

DAZ

DAZ,

http://docs.jquery.com/Main_Page is pretty good.

We use $.post because of some extra stuff we need to do, but $.ajax is probably the best option for you.

Something like this should work (warning, written in front of the TV and untested)

$("#list").droppable({
   accept: ".item",
   hoverClass: 'droppable-hover',
   drop: function(ev, ui) {
       var c = {};
       c['authenticity_token'] = encodeURIComponent(window._token);
       $.ajax({
         type: "POST",
          url: "url-to-your-rails-function",
          data: c,
          success: function(msg){
            $(this).append("<br>Dropped!");
          }
          error: function(msg) {
            # do failed stuff here
          }
       });
   }
});

Simon

Thanks for this Simon - very useful. So it seems that $.ajax is just a
more general version of $.load and $.post - still trying to figure out
the exact differences, but at least now I can gain access to the
controller and start updating model attributes. I haven't had time to
test your code, but will have a play around.

Also ... is all the authenticity_token stuff essential/best practice
or are you just using that as an example?

thanks again,

DAZ

Thanks for this Simon - very useful. So it seems that $.ajax is just a
more general version of $.load and $.post - still trying to figure out
the exact differences, but at least now I can gain access to the
controller and start updating model attributes. I haven't had time to
test your code, but will have a play around.

Also ... is all the authenticity_token stuff essential/best practice
or are you just using that as an example?

thanks again,

DAZ

That's cool.

Depends on the query I think, but it is generally required.

Rails has some rudimentary security built in to stop things (like search
bots I guess) hitting controller functions. You can try it without, but
keep an eye on the logs for an invalid authenticity token error.

Simon

Thanks again Simon, I've since noticed that all forms created by the
form_for helper have authenticity token code in too (albeit using some
ugly inline javascript!) so it id definitely something I'll look into.

On a separate note ... in your example, you simply listed
url: "url-to-your-rails-function"

How do I specify the rails functions? I guess that I can't use any
nice helpers such as tasks_path? Are the links relative to the root
directory? The actual controller action I want to access would be a
dropped action in the tasks controller, so is the url "/tasks/
dropped" ?

I really appreciate all the help you have given so far, it has really
helped me get to grips with jQueary on Rails - I'm finding it a great
way to keep the JS unobtrusive!

cheers,

DAZ

Hey DAZ,

No probs.

From our code..
         $.ajax({
             url: "/form_datas/correct/"+formId,

so, form_datas is our controller, correct is the action, and formId is the id param passed to the action

you may be able to use rails helper methods, I don't know, we just specify the URL as above.

cheers
Simon

Thanks again Simon - your help is very much appreciated!

Here are a few things I have found out - in case anybody else is
reading this:

* To get the authenticity tag to work you need this somewhere in your
view:
<%= javascript_tag "window._token = '#{form_authenticity_token}'" if
protect_against_forgery? %>

Then you can get the authenticity token by referencing window._token

* You can use nice RESTful urls and even fake out the PUT and DELETE
requests, for example

$post("/tasks/1"); will go to the show page for the task with id 1
$post("/tasks/1",{_method: "PUT",authenticity_token: encodeURIComponent
(window._token)});
will go to the update action for the task with id 1

Hope that makes sense!

cheers,

DAZ