Eu require
coloco um arquivo no topo dos meus scripts PHP. O arquivo possui apenas objeto de conexão para MySQL:
$c->new mysqli('host','usr','pass','db')
O arquivo tem 400
permissão: -r--------
e eu o mantenho /etc/mysql/
longe da raiz da minha página ( /var/www/html
).
Funciona bem, exceto que todas as noites à meia-noite ele para e recebo um erro de permissão negada para todas as minhas páginas:
Warning: require(/etc/mysql/.myfile.php): Failed to open stream: Permission denied in...
Se eu alterar as permissões para 444
, faça login no meu site e altere as permissões novamente para 400
. Funciona até a próxima meia-noite. Posso entrar e sair do meu site quantas vezes quiser ao longo do dia, mas quando chegar a meia-noite, ele falhará.
O que causa isso e como posso corrigir isso?
Obviamente gostaria de mantê-lo para que só root
possa ler o arquivo já que possui senha em texto não criptografado.
Isso deveria ser um comentário - mas o espaço é limitado e a formatação também.
Você realmente não forneceu uma boa explicação da situação.
Você disse que "perde permissões" e como restaura as operações normais, mas não disse quais são as permissões após o evento da meia-noite.
Ao determinar o acesso, as permissões não têm sentido sem detalhes de propriedade. Presumivelmente, o arquivo pertence inicialmente ao uid do seu servidor da web (embora você não tenha dito que ele estava sendo acessado por scripts executados no servidor da web). Novamente, o que são esses antes e depois?
Como você determinou que ele para à meia-noite? Saber exatamente quando o evento ocorreu é um trampolim útil para resolver o problema. Se ocorreu (digamos) entre 00:00:00 e 00:03:00, há uma probabilidade muito alta de que isso tenha ocorrido devido a alguma tarefa agendada. Também torna muito mais fácil fazer referência cruzada do evento com os logs do sistema (bem como com os logs do servidor web).
Parabéns por pensar em permissões e acesso ...
Sua escolha de permissões não é ideal. Novamente, assumindo que se trata de um servidor web, o arquivo só pode ser gerenciado pelo usuário root. Se você for a única pessoa que mantém o servidor, uma abordagem melhor seria definir a propriedade como bungee1980:wwwgrp (onde wwwgrp é o grupo padrão para o uid do servidor web) e permissões -rw-r----- (0750) .
Sua escolha de local não é ideal. A maioria dos sistemas operacionais modernos restringe o acesso a arquivos por meio de mecanismos de controle de acesso obrigatórios (SELinux no RHEL e derivados, Apparmor em outros lugares). É comum restringir o servidor web a uma árvore de diretórios contendo apenas seu conteúdo. Embora você não queira que este arquivo esteja dentro da raiz do documento por razões óbvias, você também não deseja (normalmente) permitir que seus scripts leiam diretamente de muitos outros arquivos em /etc
Um problema menor é que o PHP fornece um mecanismo para definir as credenciais padrão e os detalhes do banco de dados (e para executar código padrão adicional antes do script de destino). Dado que isso pode ser definido na configuração do seu servidor web, esse pode ser um veículo mais apropriado para as credenciais.
Em outras palavras: com permissões 400, seus scripts não podem ler o arquivo, mas com permissões 444, eles podem, e então algum processo manterá o arquivo aberto ou manterá as credenciais na RAM até meia-noite, quando algo acionará uma reinicialização ou limpeza -up de algum tipo.
Você não mencionou o sistema operacional/distribuição que está usando, mas eu começaria verificando
/etc/cron.*
os crontabs de quaisquer usuários relevantes (geralmente em/var/spool/cron[/crontabs]
ou similares) para quaisquer cron jobs diários executados à meia-noite. Talvez haja algo que limpe sessões antigas de PHP? Ou talvez estejalogrotate
desencadeando uma reinicialização de algo comophp-fpm
parte de uma programação diária de rotação de log?Se o seu sistema usa
systemd
, verifique também as unidades de temporizador:systemctl list-units --type=timer
para listar todos os temporizadores de todo o sistema e, em seguida,systemctl cat <name>.timer
visualizá-los.Por exemplo, no Debian 12,
logrotate
pode ser acionado por/etc/cron.daily/logrotate
, que pode ser executadoanacron
no horário especificado em/etc/cron.d/anacron
, por padrão, o primeiro horário entre 07h30 e 23h30 quando o sistema está em execução... mas esse agendamento será realmente usado somente sesystemd
não estiver em uso, pois o trabalho especificado em/etc/cron.d/anacron
está condicionado a/run/systemd/system
não existir.With
systemd
,logrotate.timer
é usado em vez disso e é especificado assim:Conforme descrito em
man systemd.time
,OnCalendar=daily
significa*-*-* 00:00:00
, ou seja, todos os dias exatamente à meia-noite. PermiteAccuracySec=1h
unir este temporizador com outros temporizadores que disparam entre 00:00 e 01:00, se existirem, para optimizar a poupança de energia. Pelo menos no meu sistema, o resultado final parece ser que a rotação do log acontece exatamente à meia-noite, a menos que o sistema esteja inativo naquele momento.Com
systemctl status logrotate.timer
, você pode ver o próximo horário de acionamento programado para o cronômetro.