You are here

class BotchaRecipeObscureUrl in BOTCHA Spam Prevention 6.3

Same name and namespace in other branches
  1. 6.2 controller/botcha_recipe.controller.inc \BotchaRecipeObscureUrl
  2. 7.2 controller/botcha_recipe.controller.inc \BotchaRecipeObscureUrl
  3. 7.3 controller/recipe/botcha.recipe.controller.inc \BotchaRecipeObscureUrl

Hierarchy

Expanded class hierarchy of BotchaRecipeObscureUrl

1 string reference to 'BotchaRecipeObscureUrl'
botcha_update_6200 in ./botcha.install
Implementation of hook_update_N(). Create flexible relationships between recipe books and recipes and between recipe books and forms.

File

controller/recipe/botcha.recipe.controller.inc, line 769
Controller layer of the BotchaRecipe objects.

View source
class BotchaRecipeObscureUrl extends BotchaRecipeUsingJsAbstract {
  public function getInfo() {
    parent::getInfo();
    $this->description = t('Insert a new field into form action URL.') . ' ' . t('Bots will not run JS and miss the field.') . ' ' . t('%parts is added to the form.', array(
      '%parts' => 'JS',
    )) . ' ' . t('JS enters key value into the field.');
  }
  public function isSpam($form, $form_state) {
    $isSpam = parent::isSpam($form, $form_state);
    foreach ($this->url_elements as $field => $value) {
      $url_field = isset($_GET[$field]) ? $_GET[$field] : FALSE;
      unset($_GET[$field]);
      if (isset($value['!valid_token']) && $url_field !== $value['!valid_token']) {
        $isSpam = TRUE;
        break;
      }
    }
    return $isSpam;
  }
  protected function prepare($form, $form_state) {
    parent::prepare($form, $form_state);

    // Make some preparations dependent on form before applying.
    $this->settings['form_id'] = $form['form_id']['#value'];
    $this->settings['form_action'] = $form['#action'];

    // @todo Merge url_elements with just fields.
    // @see?
    $fields = $this
      ->getProperty($this->settings['fields'], 'getFields');
    $js = $this
      ->getProperty($this->settings['js'], 'getJs');
    $this->url_elements[$fields[2]['name']] = array(
      // Describe URL field. JS will return token in URL field.
      '#type' => 'textfield',
      '#default_value' => '',
      '!valid_token' => $js['secure_token'],
    );
  }
  protected function getFieldCount() {
    return 3;
  }
  protected function getFieldName($delta) {
    switch ($delta) {
      case 2:
        return substr($this
          ->getProperty($this->seed, 'getSeed'), 1, 4) . '_name';
        break;
      case 1:
        return parent::getFieldName($delta);
        break;
      case 0:
      default:

        // @todo Remove hardcode.
        // @see?
        return 'botcha';
        break;
    }
  }
  public function getJsValue() {

    // Just ensure that parameters are set.
    $fields = $this
      ->getProperty($this->settings['fields'], 'getFields');
    $js = $this
      ->getProperty($this->settings['js'], 'getJs');
    $chops_positions = array_keys($js['chops']);
    $field2_name = $fields[2]['name'];

    // @todo Replace this workaround, find a better solution.
    // @see?
    // @todo Abstract it.
    $form_id = str_replace('_', '-', $this
      ->getSetting('form_id'));
    $submit = _botcha_url($this
      ->getSetting('form_action'), array(
      'query' => array(
        $field2_name => '__replace__',
      ),
    ));

    // Secure_token.
    $submit = preg_replace('/__replace__/', $js['chops'][$chops_positions[0]] . '\'+v+\'' . $js['chops'][$chops_positions[1]], $submit);
    if (strpos($form_id, '-node-form') !== false) {
      $js_form_id = 'node-form';
    }
    else {
      $js_form_id = $form_id;
    }

    // @todo Abstract it.
    return <<<END
Drupal.behaviors.{<span class="php-variable">$js</span>[<span class="php-string">'name'</span>]} = function() {
  \$("input.{<span class="php-variable">$fields</span>[<span class="php-constant">1</span>][<span class="php-string">'class'</span>]}").each(function() {
    f=\$(this)[0];
    if (f.value.indexOf("{<span class="php-variable">$js</span>[<span class="php-string">'match'</span>]}")==0){
      v=f.value.substring({<span class="php-variable">$js</span>[<span class="php-string">'pos'</span>]});
      \$("#{<span class="php-variable">$js_form_id</span>}").get(0).setAttribute('action', '{<span class="php-variable">$submit</span>}');
    }
  });
};
END;
  }
  public function generateFormElements() {
    $fields = $this
      ->getProperty($this->settings['fields'], 'getFields');
    return array_merge(parent::generateFormElements(), array(
      // Add hidden field to keep part of the token.
      $fields[1]['name'] => array(
        '#type' => 'hidden',
        // Store part of secure_token.
        '#default_value' => $fields[1]['default_value'],
        // @todo Abstract it.
        '#attributes' => array(
          'class' => $fields[1]['class'],
        ),
        //'#attributes' => array('class' => array($fields[1]['class'])),
        '#weight' => 20,
      ),
    ));
  }

}

Members

Namesort descending Modifiers Type Description Overrides
BotchaRecipe::$css protected property CSS to add to the page.
BotchaRecipe::$description protected property Brief description of the recipe. It should contain explanation of how bots would fail with it and what the recipe exactly does.
BotchaRecipe::$error_field public property Name of the field in the form to use in error messages (to mask botcha fields).
BotchaRecipe::$error_text public property Text to give users if botcha recipe blocks submission. It should give some help to real human users in cases of disabled Javascript or CSS.
BotchaRecipe::$id public property Identifier of the recipe.
BotchaRecipe::$js protected property Javascript to add to the page.
BotchaRecipe::$method protected property Method of recipe genration.
BotchaRecipe::$recipebooks protected property
BotchaRecipe::$secret protected property Secret.
BotchaRecipe::$settings protected property Options that received as parameters turned into settings by merging with default values.
BotchaRecipe::apply public function 1
BotchaRecipe::getDefaultSettings public function Used to get default recipe data structure. @todo ?Do we need it?
BotchaRecipe::getDescription public function
BotchaRecipe::getFieldClass protected function
BotchaRecipe::getFieldPrefix protected function
BotchaRecipe::getFields protected function
BotchaRecipe::getMethod public function
BotchaRecipe::getProperty protected function Universal getter. Wrapper getProperty is used to let class methods be used not only in getting default settings. It gives flexibility to make calls to the class methods in any order: the first of them will always calculate the property value and set…
BotchaRecipe::getSecret public function
BotchaRecipe::getSeed protected function
BotchaRecipe::getSetting public function
BotchaRecipe::getTitle public function
BotchaRecipe::handle public function Handle form depending on the result of spam check. 1
BotchaRecipe::setDescription public function
BotchaRecipe::setMethod public function
BotchaRecipe::setRecipebook public function
BotchaRecipe::setSecret public function
BotchaRecipe::setSetting public function
BotchaRecipe::setTitle public function
BotchaRecipe::__construct public function Magic method __construct.
BotchaRecipeObscureUrl::generateFormElements public function Used to get information about the recipe. Must be overridden with calling to parent::generateFormElements. @todo Switch from indexed array to associative. @see? Overrides BotchaRecipeUsingJsAbstract::generateFormElements
BotchaRecipeObscureUrl::getFieldCount protected function Overrides BotchaRecipeUsingJsAbstract::getFieldCount
BotchaRecipeObscureUrl::getFieldName protected function Overrides BotchaRecipe::getFieldName
BotchaRecipeObscureUrl::getInfo public function Used to get information about the recipe. Must be overridden. Overrides BotchaRecipeUsingJsAbstract::getInfo
BotchaRecipeObscureUrl::getJsValue public function
BotchaRecipeObscureUrl::isSpam public function Spam check. Overrides BotchaRecipe::isSpam
BotchaRecipeObscureUrl::prepare protected function Overrides BotchaRecipe::prepare
BotchaRecipeUsingJsAbstract::getCss public function Should be overridden. Overrides BotchaRecipe::getCss
BotchaRecipeUsingJsAbstract::getField protected function Overrides BotchaRecipe::getField
BotchaRecipeUsingJsAbstract::getFieldDefault protected function What server sends to JS in the field.
BotchaRecipeUsingJsAbstract::getJs public function Should be overridden. Overrides BotchaRecipe::getJs
BotchaRecipeUsingJsAbstract::getJsChops protected function
BotchaRecipeUsingJsAbstract::getJsMatch protected function What JS matches in the field.
BotchaRecipeUsingJsAbstract::getJsName protected function Get name of JS-script, attached to field.
BotchaRecipeUsingJsAbstract::getJsPos protected function What position is the part of the token.
BotchaRecipeUsingJsAbstract::getJsSecureToken protected function