You are here

trick_question.module in Trick Question 6

Same filename and directory in other branches
  1. 7 trick_question.module

trick_question.module - Main file for trick question module

Developed by Martin Joergensen, martin@vertikal.dk, Headnet.dk/Vertikal.dk Jan 2010 Version 6.0-1

File

trick_question.module
View source
<?php

/**
 * @file
 * trick_question.module - Main file for trick question module
 * 
 * Developed by Martin Joergensen, martin@vertikal.dk, Headnet.dk/Vertikal.dk Jan 2010
 * Version 6.0-1
 *
 */

/**
 * Implementation of hook_perm().
 */
function trick_question_perm() {
  return array(
    'administer trick question',
    'skip trick question',
  );
}

/**
 * Implementation of hook_help().
 */
function trick_question_help($path, $arg) {
  switch ($path) {
    case 'admin/help#trick_question':
      return '<p>Help will come</p>';
      break;
    case 'admin/settings/trick_question':
      return '<p>Set up a trick question on selected forms. A very simple Captcha-lite spam fighting solution.</p>';
      break;
  }
}

/**
 * Implementation of hook_menu().
 */
function trick_question_menu() {
  $items = array();

  // One normal menu item only: admin/settings/trick_question
  $items['admin/settings/trick_question'] = array(
    'title' => 'Trick Question',
    'description' => 'Set up Trick Question.',
    'page callback' => 'drupal_get_form',
    'page arguments' => array(
      'trick_question_admin_form',
      $void,
    ),
    'type' => MENU_NORMAL_ITEM,
    'access arguments' => array(
      'administer trick question',
    ),
  );
  return $items;
}

/**
 * Create the main form
 */
function trick_question_admin_form() {
  $form = array();

  // What question to ask
  $form['question'] = array(
    '#type' => 'textfield',
    '#size' => 120,
    '#title' => t('Question'),
    '#description' => t('Ask this question when showing the forms.'),
    '#default_value' => variable_get('trick_question_question', ''),
    '#required' => TRUE,
  );

  // What answer to give
  $form['answer'] = array(
    '#type' => 'textfield',
    '#size' => 10,
    '#title' => t('Answer'),
    '#description' => t('Only allow submissions with this answer (letter case is ignored).'),
    '#default_value' => variable_get('trick_question_answer', ''),
    '#required' => TRUE,
  );

  // Get the explanation
  $explanation = variable_get('trick_question_explanation', '');

  // Set it to default if it's not empty
  $explanation = $explanation == '' ? t('Yes, this is a trick question and easy to answer.<br />We ask it because spam bots are too stupid to answer correctly, while humans are not.') : $explanation;

  // Save it just in case the user just emptied it
  variable_set('trick_question_explanation', $explanation);

  // What question to ask
  $form['explanation'] = array(
    '#type' => 'textarea',
    '#title' => t('Explanation'),
    '#description' => t('The explanation to show to the user. Enter &lt;none&gt; for no explanation or leave empty for default explanation.'),
    '#default_value' => $explanation,
  );

  // Make a nice fieldset for the checkboxes
  $form['forms'] = array(
    '#type' => 'fieldset',
    '#title' => t('Forms'),
    '#suffix' => '<p>' . t('You can control <a href="!url">trick question per role using permissions</a>.', array(
      '!url' => url('admin/user/permissions', array(
        'query' => '#module-trick_question',
      )),
    )) . '</p>',
  );

  // Get the content types
  $node_types = node_get_types();
  foreach ($node_types as $node_type => $details) {
    $options[$node_type . '_node_form'] = t('!name (!type)', array(
      '!name' => $details->name,
      '!type' => $node_type,
    ));
  }

  // Other forms relevant
  $options['user_register'] = t('User registration');
  $options['comment_form'] = t('Comment submission');
  $forms = variable_get('trick_question_forms', array());

  // Create checkboxes
  $form['forms']['forms'] = array(
    '#type' => 'checkboxes',
    // '#title' => t('Forms'),
    '#description' => t('Add a trick question to the selected forms.'),
    '#options' => $options,
    '#default_value' => $forms,
  );

  // What question to ask
  $form['forms']['form_ids'] = array(
    '#type' => 'textarea',
    '#title' => t('Other form ID\'s'),
    '#description' => t('You can manually add the ID of any form you want to equip with a Trick Question. Write one ID on each line.'),
    '#default_value' => variable_get('trick_question_form_ids', ''),
  );

  // Buttons
  $form['buttons']['save'] = array(
    '#type' => 'submit',
    '#value' => t('Save'),
    '#weight' => 140,
  );
  $form['buttons']['cancel'] = array(
    '#type' => 'markup',
    '#value' => l(t('Cancel'), 'admin/settings'),
    '#weight' => 150,
  );
  return $form;
}

/**
 * Handle submission of admin the form
 */
function trick_question_admin_form_submit($form, &$form_state) {

  // Save the values
  variable_set('trick_question_question', $form_state['values']['question']);
  variable_set('trick_question_answer', $form_state['values']['answer']);
  variable_set('trick_question_explanation', $form_state['values']['explanation']);
  variable_set('trick_question_forms', $form_state['values']['forms']);
  variable_set('trick_question_form_ids', $form_state['values']['form_ids']);
  drupal_set_message(t('Your settings have been saved'));
}

/**
 * Hook validate
 */
function trick_question_form_validate($form, &$form_state) {

  // Check answer, ignore case
  if (drupal_strtolower($form_state['values']['trick_question']) != drupal_strtolower(variable_get('trick_question_answer', md5(time())))) {

    // Set form error for our field, let Drupal handle the rest
    form_set_error('trick_question', t('You must answer the trick question correctly.'));
  }
}

/**
 * Alter the forms and add our field
 */
function trick_question_form_alter(&$form, &$form_state, $form_id) {

  // Is user allowed to skip question then simply return
  if (user_access('skip trick question')) {
    return;
  }
  $explanation = variable_get('trick_question_explanation', t('Yes, this is a trick question and easy to answer.<br />We ask it because spam bots are too stupid to answer correctly, while humans are not.'));
  $explanation = $explanation == '<none>' ? '' : $explanation;

  // Get the standard forms
  $forms = variable_get('trick_question_forms', array());

  // Get the custom forms
  $ids = array();
  $form_ids = explode("\n", variable_get('trick_question_form_ids', ''));
  if (is_array($form_ids)) {
    foreach ($form_ids as $id) {
      if (trim($id)) {
        $ids[$id] = $id;
      }
    }
  }

  // Merge them
  $forms = array_merge($forms, $ids);
  if (array_search($form_id, $forms, TRUE)) {

    // The form in question is in our list
    // Add the trick question
    $form['trick_question'] = array(
      '#type' => 'textfield',
      '#title' => variable_get('trick_question_question', t('Error in the Trick Question setup. Contact the admin.')),
      '#size' => 20,
      '#description' => filter_xss_admin($explanation),
      '#weight' => variable_get('trick_question_weight', 0),
    );

    // Add the validation handler
    $form['#validate'][] = 'trick_question_form_validate';
  }
}

Functions

Namesort descending Description
trick_question_admin_form Create the main form
trick_question_admin_form_submit Handle submission of admin the form
trick_question_form_alter Alter the forms and add our field
trick_question_form_validate Hook validate
trick_question_help Implementation of hook_help().
trick_question_menu Implementation of hook_menu().
trick_question_perm Implementation of hook_perm().