Script para ntp fake (AKA como atualizar horário via http usando shell script)

Disclaimer:

O conteúdo deste post é histórico, mantido aqui apenas para ter exemplificar como fazer um script parsear um HTML. Para funcionar, ele depende de uma URL que não está mais disponível.
Atualmente (consultei em 31/05/2020), o Observatório Nacional disponibiliza na URL http://www.horalegalbrasil.mct.on.br/RelogioServidor.php a data em formato “epoch” que, basicamente, são quantos segundos se passaram desde a meia noite do dia 01/01/1970. Então basta converter esse número com o comando date para saber a hora atual.

Para ter uma ideia para um script, pode-se pensar em algo como:

$ date --date=@`curl -s http://www.horalegalbrasil.mct.on.br/RelogioServidor.php`

Sun May 31 18:43:43 -03 2020

E então pode-se seguir uma lógica semelhante ao que tem no restante do post se quiser que esta hora seja aplicada ao sistema.

Agradeço ao Ricardo, da Amplus, por ter informado que a URL do texto não estava mais ativa e ainda por ter sugerido essa nova URL citada acima.

Resumo da história:

Preciso que uma máquina virtual tenha a hora sempre correta mas não posso instalar o vmware tools e nem usar ntp para isso. Como fazer?

A história completa:

Tenho uma máquina virtual onde não consigo instalar o vmware-tools (máquina extremamente customizada, quase nada funciona ali sem muita modificação). Esta máquina virtual está numa rede onde não tem um servidor ntp e, para “ajudar”, o firewall desta rede não permite que eu acesse nenhum servidor ntp externo. Preciso que o horário nesta máquina esteja correto (ok, um ou outro segundo não é problema, mas a data estar na “semana passada” definitivamente não é bom).

Por sorte esta máquina consegue acessar http (via proxy, óbvio) então, tudo o que eu precisava era de uma página web que sempre tivesse a hora correta.

No Brasil, quem é o “responsável” pela hora oficial é o Observatório Nacional. Navegando pelo site deles encontrei uma url que tem a hora legal brasileira e é atualizada a cada segundo.

No meio daquela página vai ter a hora assim: 20/3/2012 15:45:38. Mas o comando date espera receber esta hora assim: 032015452012.38 (se lê de dois em dois dígitos, exceto o ano: mês; dia; hora; minuto; ano; “.” e segundo).

Então basicamente o que eu precisei é “ler” a página e “traduzir” para o formato que o comando “date” do Linux entende.

A gambiarra (AKA “solução” do problema):

Abri o source da página e tentei entender onde a data e hora estava. Vi que a hora que preciso aparece no meio de algumas tags html na terceira linha após o texto “Hora Oficial”.

O trecho do source em questão:

<TD ALIGN="CENTER" BGCOLOR=#E0FFFF><B>Hora Oficial de Brasília</B></TD>
</TR>
<TR>
<TD ALIGN="CENTER" BGCOLOR=#ffcc66><B>20/3/2012 15:45:38</B></TD>

Separei somente a linha que queria e “limpei” todas as tags, deixando somente a hora.

20/3/2012 15:45:38

Para o script ler a página, usei o comando curl, grep para procurar no texto por “Hora Oficial” e separar as próximas três linhas, tail para separar a última dessas três linhas e, finalmente, sed para remover as tags html.

O código usado (porco, confesso, mas pode rodar no seu shell) , é esse:

curl -s http://pcdsh01.on.br/HoraLegalBrasileira.asp|grep -A3 “Hora Oficial”|tail -1|sed ‘s/<TD ALIGN=”CENTER” BGCOLOR=#ffcc66><B>//g;s/<\/B><\/TD>//g’
 

Armazenei a saída desse comando numa variável, no caso “hora_full”.

Então traduzi a hora que ele me retornou para o formato do date (mais um código porco, mas está “didático”):

hora=`echo $hora_full|cut -d ” ” -f 2|cut -d : -f 1`
minuto=`echo $hora_full|cut -d ” ” -f 2|cut -d : -f 2`
segundo=`echo $hora_full|cut -d ” ” -f 2|cut -d : -f 3|tr -d ‘\r’`
mes=`echo $hora_full|cut -d “/” -f 2`
dia=`echo $hora_full|cut -d “/” -f 1`
ano=`echo $hora_full|cut -d “/” -f 3|cut -d ” ” -f 1`

E juntei tudo como parâmetro para o comando date:

date $mes$dia$hora$minuto$ano.$segundo

Se seu usuário tiver permissão para alterar a data do sistema, isto deverá “sincronizar” com o horário legal brasileiro.

PS: depois (AKA talvez um dia) eu coloque o script todo, inclusive com verificação se o usuário tem ou não permissão para acertar o horário do sistema.

2 comentários em “Script para ntp fake (AKA como atualizar horário via http usando shell script)”

  1. Muito bacana.. vou começar a deixar de lado os NTP’s ..

    Aprendendo com suas maluquices…. fiz esse abaixo, pode ser interessante para quem acessa o PC pessoal remotamente de algum lugar externo, o papel que o NOIP faz…. basta então configurar para enviar por e-mail automático qnd o pc ligar…

    $ curl -s http://meuip.datahouse.com.br | grep “meuip-home” | cut -d “;” -f2 | echo “meu ip externo é :”`cut -d “<" -f1`

    Abss

  2. Alguns anos atrás eu fiz algo interessante neste sentido (saber o IP de uma máquina remota). Usava shell script no cliente e PHP no servidor.
    Eu tinha um servidor com IP fixo e dava suporte remoto para diversas empresas cujo link era ADSL com IP dinâmico.

    Escrevi um código simples em PHP que basicamente armazenava num arquivo texto seu próprio nome (explicação abaixo), a hora de acesso e o IP de quem o acessou. Publiquei no meu webserver.

    Fiz um shell script que acessava uma url específica para cada cliente no meu servidor. A URL era o mesmo PHP, com link para ter diversos nomes diferentes (um para cada cliente). Como o PHP gravava seu próprio nome no arquivo de log, eu saberia qual cliente acessou pelo nome do arquivo (sim, é uma gambiarra), que horário e qual IP estava usando. Coloquei na crontab de cada cliente para executar a cada 15 minutos.

    Se o cliente me ligava informando algum problema, eu via no log qual o último IP que ele estava usando e acessava remotamente para o suporte.

    O segundo pior caso era o IP ter sido trocado há menos que 15 minutos, então bastaria eu esperar o tempo, ver no log o novo IP e fazer o acesso remoto. O pior caso obviamente era quando o cliente estava sem Internet, então não tinha suporte remoto ¬¬

Deixe um comentário

O seu endereço de e-mail não será publicado. Campos obrigatórios são marcados com *