We use cookies to improve your experience. No personal information is gathered and we don't serve ads. Cookies Policy.

ExpressionEngine Logo ExpressionEngine
Features Pricing Support Find A Developer
Partners Upgrades
Blog Add-Ons Learn
Docs Forums University
Log In or Sign Up
Log In Sign Up
ExpressionEngine Logo
Features Pro new Support Find A Developer
Partners Upgrades
Blog Add-Ons Learn
Docs Forums University Blog
  • Home
  • Forums

Best/Proper method for CP AJAX Posts?

Development and Programming

Jack McDade's avatar
Jack McDade
425 posts
15 years ago
Jack McDade's avatar Jack McDade

I’ve come at this a few different ways and there doesn’t seem to be any documentation or forum threads speaking to the proper, best practices method of implementing a Control Panel-side AJAX post. Here are my thoughts, would love to hear back from anyone on this.

Option 1: Action ID

One of the most obvious choices would be to register an Action ID for your module to post to. Quick, clean and straightforward (tho very little documentation exists on them in general). the biggest downfall to this method, however, is MSM sites. I’ve noticed when you need to run specific database type methods on one site or another, the Control Panel isn’t always too kind when passing the site_id (depending on which site you’re logged into, your session/cookie preferences, proper site_short_name configuration, renamed index.php file, various installed extensions such as Freebie, etc). This can cause some potential issues.

Option 2: MCP Method

I’ve experimented with using a Control Panel url (e.g. &C=addons_modules&M=show_module_cp&module=module_name&method=ajax_function) to process the AJAX post in EE1, which works well if you flush the output buffer and exit() after your function, but this doesn’t work in EE2. EE2 seems to intercept the url and move any post data into GET parameters and redirect you to the CP homepage. This appears to be JavaScript/jQuery functionality intercepting the call, so I tried to use noConflict namespacing but to no avail. I saw a “process_” prefix thread in reference to Accessories, but nothing similar for Modules.

Option 3: You tell me

Not sure what else to try. Perhaps I’ve missed some memo along the way and I’m hoping someone can point me in the right direction.

       
Rob Sanchez's avatar
Rob Sanchez
335 posts
15 years ago
Rob Sanchez's avatar Rob Sanchez

Option 2 works for me if I do this in my MCP method

function ajax_function() {
    return $this->EE->output->send_ajax_response($array);
}

And my ajax call:

$.getJSON(EE.BASE+"&C=addons_modules&M=show_module_cp&module=module_name&method=ajax_function", {}, function(data) {
    //whatever
});
       
Jack McDade's avatar
Jack McDade
425 posts
15 years ago
Jack McDade's avatar Jack McDade

This method works when using GET, but has lots of issues when trying to POST. Any thoughts there?

       
Manuel Payano's avatar
Manuel Payano
144 posts
15 years ago
Manuel Payano's avatar Manuel Payano

The only reliable way we found that is using ACT. The only problem we noticed is when posting file uploads to the ACT URL while the system is OFF.

Using an Module Page as the AJAX url doesn’t work if the user does not have access (permission) to the Module.

Would love to hear other thoughts.

       
Jack McDade's avatar
Jack McDade
425 posts
15 years ago
Jack McDade's avatar Jack McDade

I finally found another way to do this, using methods in the MCP. The problem i had before was having the POST redirected while GET would go through (not what i needed however). Apparently, the system prevents any POST data from being submitted in the CP unless it’s using Secure Forms.

So by targeting the method and adding an &XID; query string with the value from XID_SECURE_HASH, it would allow processing. I’m still testing and looking for any pitfalls here (member permissions is actually a bonus in this case), but it looks promising.

       
Michiel Papenhove's avatar
Michiel Papenhove
9 posts
15 years ago
Michiel Papenhove's avatar Michiel Papenhove

Well, it doesn’t matter what I use, EE just returns the entire control page instead of my AJAX response. As long as I just use GET calls, the MCP option works fine. As soon as I switch to POST calls, everything fails. Also tried adding the XID parameter in the query string but no happy moments there. Even worse: if I properly register an action and I use the ?ACT=xx way of calling EE, I still end up with a control page instead of an AJAX response. Switch to GET and all is fine, but I just don’t want to use GET calls due to the amount of actual data that will be send around.

I’d love to see how Jack got his code working because I’m having a very hard time getting something that seems so simple to actually work :(

Another thought/question: isn’t the XID hash supposed to change everytime someone performs an action? If you add the XID hash to JavaScript code that does the AJAX call, isn’t it sort of hardcoded, resulting in even more problems?

And something else to conclude: it’s nice to see that EE finally incorporates stuff like jQuery but would it perhaps be an idea to actually create some documentation on using AJAX stuff with EE2 and the control panel? This current path of trial and error sure isn’t the most effective…

       
Michiel Papenhove's avatar
Michiel Papenhove
9 posts
15 years ago
Michiel Papenhove's avatar Michiel Papenhove

Got it. Interpreted Jack’s suggestion wrong, fixed that and now it is working. For those who have the same problem, the following should work:

First define a constant (not actually necessary but keeps things a bit more readable)

define('AJAX_URL', html_entity_decode(BASE).'&C=addons_modules&M=show_module_cp&module=modulename');

Then construct a piece of JavaScript code to perform the actual call:

function connectToFeedInputType()
{
    $('#feedUrl').blur(function()
    {
        // Get the uri that was submitted
        var url = $('#feedUrl').attr('value');
        $.ajax({ url: '<?php echo AJAX_URL.'&method=check_uri'; ?>',
        type:"POST",
        data: { XID:"<?php echo XID_SECURE_HASH; ?>", uri:url },
        success: function(response) { handleFeed(response); } });
    });
}

The thing that fixed it is as Jack stated but which I did wrong at first. You need to add the XID variable to the actual javascript data array, not to the action URL. In other words, it needs to be “POST-ed”.

Hope this helps other people.

p.s.: still not sure about the XID changing. Any pointers would be appreciated.

       
Jack McDade's avatar
Jack McDade
425 posts
15 years ago
Jack McDade's avatar Jack McDade
still not sure about the XID changing. Any pointers would be appreciated.

Glad you got it working! Apologies if I was unclear. As far as the XID changing – the TTL is set for 4 hours on a specific ID (line 30 of libraries/CP.php), so unless your users keep interacting with the AJAX without refreshing the page or doing anything else for a REALLY long time, you should be safe.

       
Michiel Papenhove's avatar
Michiel Papenhove
9 posts
15 years ago
Michiel Papenhove's avatar Michiel Papenhove

Aha 😊 Four hours is indeed more than enough. Glad to know. And thanks for helping me out in the first place!

       
Jack McDade's avatar
Jack McDade
425 posts
15 years ago
Jack McDade's avatar Jack McDade

Glad to! I’ll let you know if i run into any edge case issues with it, and if you could do the same that would be great. But otherwise, all ahead forward!

       
Michiel Papenhove's avatar
Michiel Papenhove
9 posts
15 years ago
Michiel Papenhove's avatar Michiel Papenhove

If I stumble upon more issues that need fixing, I will of course list them in this topic. No problem 😊

       
Green Egg Media's avatar
Green Egg Media
111 posts
15 years ago
Green Egg Media's avatar Green Egg Media

Just wanted to point out that if you are going straight Javascript the XID hash is available as EE.XID, so this works:

data: { XID:EE.XID }

I wish this was more documented! Was driving me crazy for a while.

       
Dom Stubbs's avatar
Dom Stubbs
156 posts
15 years ago
Dom Stubbs's avatar Dom Stubbs

This is an incredibly handy thread, thanks to everyone who’s chimed in. Green Egg Media’s suggestion is particularly useful.

A lot of this stuff should be in the docs.

       
Adam Khan's avatar
Adam Khan
319 posts
13 years ago
Adam Khan's avatar Adam Khan

Remove comment, already mentioned above.

       
Man With A Peg's avatar
Man With A Peg
124 posts
13 years ago
Man With A Peg's avatar Man With A Peg
Just wanted to point out that if you are going straight Javascript the XID hash is available as EE.XID, so this works:
data: { XID:EE.XID }

Beautiful. This is allowing me to perform repeated AJAX calls that were failing before, even when I passed back a new XID in the AJAX response (XID_SECURE_HASH) and used that. Thanks!

       

Reply

Sign In To Reply

ExpressionEngine Home Features Pro Contact Version Support
Learn Docs University Forums
Resources Support Add-Ons Partners Blog
Privacy Terms Trademark Use License

Packet Tide owns and develops ExpressionEngine. © Packet Tide, All Rights Reserved.