
Bom dia No artigo, mostrarei como é possível para usuários comuns de hospedagem capturar endereços IP que geram carga excessiva no site e depois bloqueá-los usando ferramentas de hospedagem; haverá "um pouco" de código php, algumas capturas de tela.
Dados de entrada:- Site criado no CMS WordPress
- Hosting Beget (este não é um anúncio, mas as capturas de tela do painel de administração serão deste provedor de hospedagem)
- O site WordPress foi lançado em algum lugar no início de 2000 e possui um grande número de artigos e materiais.
- Versão do PHP 7.2
- WP tem a versão mais recente
- Já faz algum tempo que o site começou a gerar uma alta carga no MySQL de acordo com a hospedagem. Todos os dias, esse valor excede 120% da norma por conta
- De acordo com Yandex. O site métrico é visitado por 100 a 200 pessoas por dia
Primeiro de tudo, foi feito:- Os bancos de dados são limpos de lixo acumulado
- Plugins desnecessários estão desabilitados, seções de código desatualizado são removidas
Ao mesmo tempo, chamo a atenção para as opções de cache (plugins de cache), fizemos observações - mas a carga de 120% de um site permaneceu inalterada e só pôde crescer.Como era a carga aproximada nos bancos de dados de hospedagem
No topo está o site em questão, logo abaixo de outros sites que têm o mesmo cms e aproximadamente o mesmo tráfego, mas criam menos carga.Análise- Muitas tentativas foram feitas com opções para armazenar dados em cache, observações foram feitas por várias semanas (o benefício de hospedar durante esse período nunca escrevi que sou tão ruim e me desconectou)
- Houve uma análise e pesquisa de consultas lentas, depois a estrutura do banco de dados e o tipo de tabela foram ligeiramente alterados
- Para análise, o AWStats interno foi usado principalmente (a propósito, ajudou a calcular o endereço IP mais ruim por volume de tráfego
- Métrica - a métrica fornece informações apenas sobre pessoas, não sobre bots
- Houve tentativas de usar plug-ins para o WP, que podem filtrar e bloquear os visitantes mesmo por país de localização e por várias combinações
- Uma maneira completamente radical acabou sendo fechar o site por um dia com a marca “Estamos em manutenção” - isso também foi feito usando o famoso plug-in. Nesse caso, esperamos que a carga caia, mas não para os valores à esquerda de 0, já que a ideologia do WP é baseada em ganchos e plugins iniciam sua atividade quando ocorre algum tipo de "gancho" e, antes que o "gancho" ocorra, consultas ao banco de dados já podem ser feitas.
Idéia- Calcule endereços IP que fazem muitas solicitações em um curto período de tempo.
- Corrija o número de visitas ao site
- Com base no número de acessos, bloqueia o acesso ao site
- Bloqueie usando a entrada "Negar de" no arquivo .htaccess
- Outras opções, como iptables e regras para o Nginx, sem considerar, porque eu escrevo sobre hospedagem
Uma ideia surgiu, então você tem que implementá-la, pois sem ela ...
- Criamos tabelas para acumulação de dados
CREATE TABLE `wp_visiters_bot` ( `id` INT(11) NOT NULL AUTO_INCREMENT, `ip` VARCHAR(300) NULL DEFAULT NULL, `browser` VARCHAR(500) NULL DEFAULT NULL, `cnt` INT(11) NULL DEFAULT NULL, `request` TEXT NULL, `input` TEXT NULL, `data_update` DATETIME NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, PRIMARY KEY (`id`), UNIQUE INDEX `ip` (`ip`) ) COMMENT=' ' COLLATE='utf8_general_ci' ENGINE=InnoDB AUTO_INCREMENT=1;
CREATE TABLE `wp_visiters_bot_blocked` ( `id` INT(11) NOT NULL AUTO_INCREMENT, `ip` VARCHAR(300) NOT NULL, `data_update` DATETIME NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, PRIMARY KEY (`id`), UNIQUE INDEX `ip` (`ip`) ) COMMENT=' ' COLLATE='utf8_general_ci' ENGINE=InnoDB AUTO_INCREMENT=59;
CREATE TABLE `wp_visiters_bot_history` ( `id` INT(11) NOT NULL AUTO_INCREMENT, `ip` VARCHAR(300) NULL DEFAULT NULL, `browser` VARCHAR(500) NULL DEFAULT NULL, `cnt` INT(11) NULL DEFAULT NULL, `data_update` DATETIME NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP, `data_add` DATETIME NULL DEFAULT CURRENT_TIMESTAMP, PRIMARY KEY (`id`), UNIQUE INDEX `ip` (`ip`) ) COMMENT=' ' COLLATE='utf8_general_ci' ENGINE=InnoDB AUTO_INCREMENT=1;
- Crie um arquivo no qual colocaremos o código. O código será escrito na tabela de candidatos para bloqueio e manterá um histórico para depuração.
Código de arquivo para gravar endereços IP <?php if (!defined('ABSPATH')) { return; } global $wpdb; function coderun_get_user_ip() { $client_ip = ''; $address_headers = array( 'HTTP_CLIENT_IP', 'HTTP_X_FORWARDED_FOR', 'HTTP_X_FORWARDED', 'HTTP_X_CLUSTER_CLIENT_IP', 'HTTP_FORWARDED_FOR', 'HTTP_FORWARDED', 'REMOTE_ADDR', ); foreach ($address_headers as $header) { if (array_key_exists($header, $_SERVER)) { $address_chain = explode(',', $_SERVER[$header]); $client_ip = trim($address_chain[0]); break; } } if (!$client_ip) { return ''; } if ('0.0.0.0' === $client_ip || '::' === $client_ip || $client_ip == 'unknown') { return ''; } return $client_ip; } $ip = esc_sql(coderun_get_user_ip());
A essência do código é obter o endereço IP do visitante e gravá-lo na tabela. Se o ip já estiver na tabela, o campo cnt será aumentado (o número de solicitações ao site) - Agora é assustador ... Agora eles vão me queimar por minhas ações :)
Para gravar todas as chamadas para o site, incluímos o código do arquivo no arquivo principal do WordPress - wp-load.php. Sim, modificamos o arquivo do kernel precisamente depois que a variável global $ wpdb já existe
Agora, podemos ver com que frequência esse ou aquele endereço IP é anotado em nossa tabela e, com uma xícara de café, olhamos para lá a cada 5 minutos para entender a imagem.

Em seguida, basta copiar o IP "nocivo", abrir o arquivo .htaccess e adicioná-lo ao final do arquivo
Order allow,deny Allow from all # start_auto_deny_list Deny from 94.242.55.248 # end_auto_deny_list
Tudo, agora 94.242.55.248 - não tem acesso ao site e não gera uma carga no banco de dados
Mas cada vez que copiar com suas próprias mãos não é uma tarefa muito justa e, além disso, o código foi concebido como autônomo
Adicione um arquivo que será executado pelo CRON a cada 30 minutos:
Código do arquivo que modifica .htaccess <?php if (empty($_REQUEST['key'])) { die('Hello'); } require('wp-load.php'); global $wpdb; $limit_cnt = 70;
O código do arquivo é bastante simples e primitivo e sua principal idéia é levar candidatos para o bloqueio e inserir as regras de bloqueio no arquivo .htaccess entre comentários
# start_auto_deny_list e # end_auto_deny_list
Agora, o ip "nocivo" é bloqueado por eles mesmos e o arquivo .htaccess se parece com isso:
# BEGIN WordPress <IfModule mod_rewrite.c> RewriteEngine On RewriteBase / RewriteRule ^index\.php$ - [L] RewriteCond %{REQUEST_FILENAME} !-f RewriteCond %{REQUEST_FILENAME} !-d RewriteRule . /index.php [L] </IfModule> # END WordPress Order allow,deny Allow from all # start_auto_deny_list Deny from 94.242.55.248 Deny from 207.46.13.122 Deny from 66.249.64.164 Deny from 54.209.162.70 Deny from 40.77.167.86 Deny from 54.146.43.69 Deny from 207.46.13.168 ....... # end_auto_deny_list
Como resultado, após o início da ação desse código, você pode ver o resultado no painel de hospedagem:
PS: O material é protegido por direitos autorais, embora eu tenha publicado parte dele no meu site, mas no Habre uma versão mais expandida foi obtida.