You are here

ip_ban.module in IP Ban 7

Same filename and directory in other branches
  1. 8 ip_ban.module

File

ip_ban.module
View source
<?php

/**
 * @file
 * Module can "ban" or set site to "read only" by country or IP address.
 *
 * Permissions, administration menu item, form, form theme, form validation,
 * and code for handling read-only and banned IP addresses by country or
 * individually.
 */
include_once DRUPAL_ROOT . '/includes/locale.inc';
define('IP_BAN_NOBAN', 0);
define('IP_BAN_READONLY', 1);
define('IP_BAN_BANNED', 2);

/*
 * Todo:
 * 1) hook_help
 * 2) tests
 */

/**
 * Implements hook_permission().
 */
function ip_ban_permission() {
  return array(
    'ignore ip_ban' => array(
      'title' => t('Bypass ban'),
      'description' => t('Allow a user from a banned IP address or country to bypass read only or complete ban.'),
    ),
  );
}

/**
 * Implements hook_menu().
 */
function ip_ban_menu() {
  $items = array();
  $items['admin/config/ip_ban'] = array(
    'title' => 'IP Ban',
    'description' => 'Set IP addresses and/or countries to read only, or ban them entirely.',
    'page callback' => 'drupal_get_form',
    'page arguments' => array(
      'ip_ban_admin',
    ),
    'access arguments' => array(
      'administer site configuration',
    ),
    'type' => MENU_NORMAL_ITEM,
    'file' => 'ip_ban.admin.inc',
  );
  return $items;
}

/**
 * Implements hook_theme().
 */
function ip_ban_theme() {
  $themes = array(
    'ip_ban_country_table' => array(
      'render element' => 'ip_ban_table',
    ),
  );
  return $themes;
}

/**
 * Implements hook_block_list_alter().
 */
function ip_ban_block_list_alter(&$blocks) {

  // Take no action if the user has the "Bypass ban" permission.
  if (user_access('ignore ip_ban')) {
    return;
  }
  $banvalue = _ip_ban_set_ban_value();
  $disabled_blocks = variable_get('ip_ban_disabled_blocks');
  $disabled_block_list = array();
  if (!empty($disabled_blocks)) {
    $disabled_block_array = explode(PHP_EOL, $disabled_blocks);
    foreach ($disabled_block_array as $disabled_block) {
      $disabled_block_list[] = preg_replace('/\\s+/', '', $disabled_block);
    }
  }
  if (!empty($disabled_block_list)) {
    foreach ($blocks as $key => $block) {
      if ($block->status == 1) {
        $block_module_delta = $block->module . ',' . $block->delta;
        if (in_array($block_module_delta, $disabled_block_list)) {
          unset($blocks[$key]);
        }
      }
    }
  }
  _ip_ban_determine_action($banvalue);
}

/**
 * Function sets user's ban value (if any).
 *
 * Load the user's country code based on their IP address, then check if
 * that country is set to complete ban, read-only, or has no access
 * restrictions. We then do the same for any additional read-only or complete
 * ban IP addresses added. If the user matched a country or an IP address
 * entered, then they are shown a message and/or redirected based on complete
 * ban or read-only.
 */
function _ip_ban_set_ban_value() {

  // If code is being run from drush, we don't want to take any action.
  if (drupal_is_cli() && function_exists('drush_main')) {
    return;
  }
  $test_ip = variable_get('ip_ban_test_ip', '');

  // Grab the test IP address or the user's real address.
  $ip = empty($test_ip) ? ip_address() : $test_ip;
  $country_code = ip2country_get_country($ip);

  // Determine if the current user is banned or read only.
  // Individual IP complete ban trumps individual read only IP, both of which
  // trump a country setting.
  // Load the country-wide setting.
  $banvalue =& drupal_static(__FUNCTION__);
  if (!isset($banvalue)) {
    $banvalue = (int) variable_get('ip_ban_' . $country_code, IP_BAN_NOBAN);

    // Check the read-only IP list.
    $readonly_ips = variable_get('ip_ban_readonly_ips', '');
    if (!empty($readonly_ips)) {
      $ip_readonly_array = explode(PHP_EOL, $readonly_ips);
      if (in_array($ip, $ip_readonly_array)) {
        $banvalue = IP_BAN_READONLY;
      }
    }

    // Check the complete ban list.
    $banned_ips = variable_get('ip_ban_additional_ips', '');
    if (!empty($banned_ips)) {
      $ip_ban_array = explode(PHP_EOL, $banned_ips);
      if (in_array($ip, $ip_ban_array)) {
        $banvalue = IP_BAN_BANNED;
      }
    }
  }
  return $banvalue;
}

/**
 * Function determines action based on current user's ban setting.
 */
function _ip_ban_determine_action($banvalue) {
  if ($banvalue === IP_BAN_READONLY) {
    $uri = check_plain(filter_xss($_GET['q']));
    if ($uri == 'user' || strpos($uri, 'user/') !== FALSE) {
      drupal_set_message(t(variable_get('ip_ban_readonly', 'You may not create an account, attempt to log in, or request a password change from your current location.')), 'error');
      drupal_goto(variable_get('ip_ban_readonly_path', ''));
    }
  }
  if ($banvalue === IP_BAN_BANNED) {

    // Always allow access to the banned page.
    $complete_ban_path = variable_get('ip_ban_completeban_path');
    if (!empty($complete_ban_path) && check_plain(filter_xss($_GET['q'])) != drupal_get_normal_path($complete_ban_path)) {
      drupal_goto($complete_ban_path);
    }
    else {
      drupal_set_message(t(variable_get('ip_ban_completeban', 'You may not view this site from your current location.')), 'error');
    }
  }
}

Functions

Namesort descending Description
ip_ban_block_list_alter Implements hook_block_list_alter().
ip_ban_menu Implements hook_menu().
ip_ban_permission Implements hook_permission().
ip_ban_theme Implements hook_theme().
_ip_ban_determine_action Function determines action based on current user's ban setting.
_ip_ban_set_ban_value Function sets user's ban value (if any).

Constants