Using Drupal wildcard loader to access $_POST variables in my hook menu page callback

Tools

The Issue

Some specific tasks on Drupal-based API development which involves processing third party data like incoming ajax calls or POST requests may require that you will have to deal with these POST params directly somewhere within your drupal code but they might be not be available at the point due to other modules acitions or whatever.

By default, when data flow containing POST or GET values comes to page callback function defined in hook menu, those variables are usually available and accessible.

However, in my case, during work on one of Drupal 7 projects, the POST variables were empty despite that they were present at the bootstrap stage.

Solution

So I had to research this issue a little bit and found that it was caused by client's "do not touch code", so I came up to solution to use wildcard loader custom function as a bridge to my POST data.

Drupal documentation on using wildcard loader arguments can be found here: https://www.drupal.org/node/224170.

What is wildcard loader function?

In short, this is a custom function which should live in the same .module file where you define your hook menu which supposed to use this wildcard.

The name of the function should always end with _load part, for example:

input_data_load, where input_data is your made up custom name.

The name of the loader function (without _load ending) must be put into menu path like this:  %input_data
Make sure you do not forget to remove _load ending part.

The full code example is below.

Example

<?php
/**
 * @file
 * Wildcard loader example
 */

/**
 * Implements hook_menu().
 * 
 * Wildcard loader function input_data_load is set for the process/% path.
 */
function page_processor_menu() {
  $items['process/%input_data'] = [
    'title' => 'Page Processor Menu',
    'page callback' => '_page_processor_menu_page_callback',
    'page arguments' => [1],
    'access arguments' => ['access content'],
    'type' => MENU_CALLBACK,
  ];

  return $items;
}

/**
 * Wildcard argument loader function
 *
 * @param array
 *   Array input.
 *
 * @return mixed
 *  An associative array.
 */
function input_data_load($query) {
  $data['query'] = $query;
  if (!empty($_POST['my_key'])) {
    $data['my_key'] = check_plain($_POST['my_key']);
    // do some checks and fun stuff with data
  }
  return !empty($data) ? $data : FALSE;
}

/**
 * Implements page callback function
 *
 * @param array
 *   Array input.
 *
 * @return string
 *  Callback result.
 */
function _page_processor_menu_page_callback($data) {
  // here we have our POST my_key variable available.
  if (!empty($data['my_key'])) {
    // do your stuff
    $a = $data['my_key'];
  }

  return empty($a) ? 'No key provided ' : 'Your key is ' . $a;
}

Conclusion

I must say, that above implementation is very specific due to the issue I had, however, usign wildcard loader functions can be very helpful.

They can preprocess incoming data by any way you want and provide arrays, node or entity objects to menu callbacks, depending on your logic.

Add new comment

CAPTCHA
This question is for testing whether or not you are a human visitor and to prevent automated spam submissions.