[PHP] Jak pobrać aktualny czas za pomocą potokołu TIME z serwerów będących wzorcami czasu?

0x01 graphic

Chcesz pobrać aktualny czas za pomocą protokołu TIME z serwerów będących wzorcami czasu.

0x01 graphic

Aby uzyskać aktualny czas możesz wykorzystać specjalne serwery będące wzorcami czasu, które podają najdokładniejszy czas w Sieci. Są one synchronizowane z atomowymi wzorcami czasu.

Aby połączyć się z takimi serwerami możesz skorzystać z prostej usługi wykorzystującej protokół TIME i działającej na porcie 37 serwera udostępniającego czas.

Serwery takie udostępniają aktualny czas w postaci 32-bitowego znacznika czasu określającego ilość sekund, jaka upłynęła od daty 1900.01.01 00:00:00 UTC. Mając taki znacznik można łatwo wyciągnąć dzień, godzinę czy minutę aby dowolnie obrabiać datę i pokazywać ją w formacie jaki tylko zechcemy.

Pobierzmy aktualną datę i przedstawmy ją w postaci: YYYY.MM.DD GG:MM:SS.

<?

$f = fsockopen("ntp.task.gda.pl",37);

if ($f) {

$czas = fread($f,100);

fclose($f);

$czas=hexdec(bin2hex($czas));

$czas = date("Y-m-d H:i:s",$czas-2208988800);

} else {

$czas="Nie można nawiązać połączenia z serwerem";

}

echo "Aktualny czas: $czas";

?>

Za pomocą fsockopen() łączymy się z serwerem czasu na porcie 37. Jeżeli udało się wykonać połączenie, pobieramy np. 100 znaków za pomocą funkcji fread() i zamykamy połączenie. Jeżeli nie, zmiennej $czas możemy przypisać jakiś komunikat mówiący o tym, że połączenie nie zostało zrealizowane.

Pobrane znaki zapisane są na 32 bitach, a więc zajmują 4 bajty (4 znaki). Musimy je przekonwertować za pomocą bin2hex() z wersji binarnej na szesnastkową aby dała się wyświetlić na ekranie, a najlepiej od razu zamienić ją do liczby dziesiętnej stosując funkcję hexdec().

Mamy już znacznik czasu w postaci dziesiętnej, czyli liczbę sekund od roku 1900. Ponieważ znacznik czasu w systemach Unix i w PHP zaczyna się od roku 1970, musimy odjąć od aktualnej daty 70 lat (2208988800 sekund) aby otrzymać znacznik nadający się do stosowania w funkcjach czasu PHP.

Teraz wystarczy sformatować czas według dowolnych kryteriów i podać do funkcji date() wyliczony znacznik, aby uzyskać datę na podstawie danych z serwera czasu.

Problemem może okazać się znalezienie działających serwerów czasu, oto kilka z nich: ntp.task.gda.pl, ntp.icm.edu.pl, time.nrc.ca, time.ien.it.