Python ntplib 响应中的所有字段是什么?如何使用它们?
What are all the fields in a Python ntplib response, and how are they used?
我想测量本地时钟和
一个远程处理器 运行 一个 NTP 服务器。
我可以获得响应的 tx_time,如下所示,但更好的估计应该包括一些网络延迟估计。 NTP 响应消息中还有其他字段也应该使用。
import ntplib
from time import ctime,time
addr_remote = '128.128.204.207'
c = ntplib.NTPClient()
remote = c.request(addr_remote)
local = time()
print("REMOTE: " + ctime(remote.tx_time) + " <reference clock> ")
print("LOCAL: " + ctime(local) + " delta: " + str(local - remote.tx_time ))
如果我看"remote":
for attr in dir(remote):
print("remote.%s = %r" % (attr, getattr(remote, attr)))
我明白了:
remote.delay = 0.0
remote.dest_time = 1531863145.9309998
remote.dest_timestamp = 3740851945.9309998
remote.from_data = <bound method NTPPacket.from_data of <ntplib.NTPStats object at 0x000000000265B2E8>>
remote.leap = 0
remote.mode = 4
remote.offset = -1.8789582252502441
remote.orig_time = 1531863145.9309998
remote.orig_timestamp = 3740851945.9309998
remote.poll = 0
remote.precision = -7
remote.recv_time = 1531863144.0520415
remote.recv_timestamp = 3740851944.0520415
remote.ref_id = 0
remote.ref_time = 0.0
remote.ref_timestamp = 2208988800.0
remote.root_delay = 0.0
remote.root_dispersion = 0.0
remote.stratum = 9
remote.to_data = <bound method NTPPacket.to_data of <ntplib.NTPStats object at 0x000000000265B2E8>>
remote.tx_time = 1531863144.0520415
remote.tx_timestamp = 3740851944.0520415
那么,我该如何使用这些:
- dest_time
- orig_time
- recv_time
- tx_time
消除网络延迟,并更好地估计时钟差异?
NTP 客户端发送一个带有本地时间 orig_time
的数据包,NTP 服务器在服务器时间 recv_time
收到该数据包。然后服务器在服务器时间 tx_time
回复,客户端在当地时间 dest_time
.
收到回复
往返delay
计算为recv_time - orig_time + dest_time - tx_time
,时钟之间的偏移量为offset = (recv_time - orig_time + tx_time - dest_time) / 2
。
假设两个NTP数据包走的路径一致,正确的调整时间就是dest_time + offset
,相当于tx_time + delay/2
.
我在尝试将我的客户端计算机同步到 NTP 时间并检查它是否实际同步时找到了这个答案。基于@Vic,这意味着客户端时钟(与服务器 NTP 时钟相比)总是关闭:
dest_time + offset = tx_time + delay/2
dest_time - tx_time = delay/2 - offset
即
correction = delay/2 - offset
正如@Vic 所说,数据包可能采用不同的路由进出,但平均而言 correction
应该给你你的时钟偏移(我认为)。即使通过 time.nist.gov
与 os.system('w32tm /resync/nowait')
同步,我的计算机也总是以某种方式关闭 40 毫秒。欢迎评论!
这是我的代码。
import ntplib
from datetime import datetime, timezone
def get_ntp_time():
ntp_pool = ['pool.ntp.org', 'time.nist.gov']
def call_ntp(serverAddress):
call = ntplib.NTPClient()
return call.request(server, version=3)
for server in ntp_pool:
response = call_ntp(server)
print(f"server: {server}")
print(f"request packet sent (as LOCAL client time, orig_time): {datetime.fromtimestamp(response.orig_time, timezone.utc)}")
print(f"request packet received (as NTP server time, recv_time): {datetime.fromtimestamp(response.recv_time, timezone.utc)}")
print(f"response packet sent (as NTP server time, tx_time): {datetime.fromtimestamp(response.tx_time, timezone.utc)}")
print(f"response packet received (as LOCAL client time, dest_time): {datetime.fromtimestamp(response.dest_time, timezone.utc)}")
print(f'round trip duration: {response.delay} s')
print(f'* adjusted time, tx_time + delay/2: {datetime.fromtimestamp(response.tx_time + response.delay/2, timezone.utc)}')
print(f'* adjusted time, dest_time + offset: {datetime.fromtimestamp(response.dest_time + response.offset, timezone.utc)}')
print(f'correction to client: {response.delay/2 - response.offset} s\n')
# for attr in dir(response):
# if not attr .startswith('_'):
# print("response.%s = %r" % (attr, getattr(response, attr)))
print('-')
get_ntp_time()
回复:
server: pool.ntp.org
request packet sent (as LOCAL client time, orig_time): 2021-04-23 16:14:46.544797+00:00
request packet received (as NTP server time, recv_time): 2021-04-23 16:14:46.535852+00:00
response packet sent (as NTP server time, tx_time): 2021-04-23 16:14:46.535862+00:00
response packet received (as LOCAL client time, dest_time): 2021-04-23 16:14:46.579710+00:00
round trip duration: 0.03490257263183594 s
* adjusted time, tx_time + delay/2: 2021-04-23 16:14:46.553314+00:00
* adjusted time, dest_time + offset: 2021-04-23 16:14:46.553314+00:00
correction to client: 0.04384756088256836 s
-
server: time.nist.gov
request packet sent (as LOCAL client time, orig_time): 2021-04-23 16:14:46.642192+00:00
request packet received (as NTP server time, recv_time): 2021-04-23 16:14:46.641157+00:00
response packet sent (as NTP server time, tx_time): 2021-04-23 16:14:46.641158+00:00
response packet received (as LOCAL client time, dest_time): 2021-04-23 16:14:46.689054+00:00
round trip duration: 0.04686117172241211 s
* adjusted time, tx_time + delay/2: 2021-04-23 16:14:46.664588+00:00
* adjusted time, dest_time + offset: 2021-04-23 16:14:46.664588+00:00
correction to client: 0.0478968620300293 s
-
我发现前面的回答对dealy或offset(延迟的一半)计算有点迷惑。我想指出这一点。
原来,ntplib.py源,dest_timestamp(接收时间),orig_timestamp(发送时间)是本地(客户端)时间。 tx_timestamp(服务器发送时间)和recv_timestamp(服务器接收时间)是服务器时间。所以以下代码中的第一项表示数据包发送和接收差异,第二项表示服务器处理时间。
无论如何,调整后的时间可以这样计算
adjusted_time = response.tx_time + response.delay*0.5
@property
def delay(self):
"""round-trip delay"""
return ((self.dest_timestamp - self.orig_timestamp) -
(self.tx_timestamp - self.recv_timestamp))
我想测量本地时钟和 一个远程处理器 运行 一个 NTP 服务器。
我可以获得响应的 tx_time,如下所示,但更好的估计应该包括一些网络延迟估计。 NTP 响应消息中还有其他字段也应该使用。
import ntplib
from time import ctime,time
addr_remote = '128.128.204.207'
c = ntplib.NTPClient()
remote = c.request(addr_remote)
local = time()
print("REMOTE: " + ctime(remote.tx_time) + " <reference clock> ")
print("LOCAL: " + ctime(local) + " delta: " + str(local - remote.tx_time ))
如果我看"remote":
for attr in dir(remote):
print("remote.%s = %r" % (attr, getattr(remote, attr)))
我明白了:
remote.delay = 0.0
remote.dest_time = 1531863145.9309998
remote.dest_timestamp = 3740851945.9309998
remote.from_data = <bound method NTPPacket.from_data of <ntplib.NTPStats object at 0x000000000265B2E8>>
remote.leap = 0
remote.mode = 4
remote.offset = -1.8789582252502441
remote.orig_time = 1531863145.9309998
remote.orig_timestamp = 3740851945.9309998
remote.poll = 0
remote.precision = -7
remote.recv_time = 1531863144.0520415
remote.recv_timestamp = 3740851944.0520415
remote.ref_id = 0
remote.ref_time = 0.0
remote.ref_timestamp = 2208988800.0
remote.root_delay = 0.0
remote.root_dispersion = 0.0
remote.stratum = 9
remote.to_data = <bound method NTPPacket.to_data of <ntplib.NTPStats object at 0x000000000265B2E8>>
remote.tx_time = 1531863144.0520415
remote.tx_timestamp = 3740851944.0520415
那么,我该如何使用这些:
- dest_time
- orig_time
- recv_time
- tx_time
消除网络延迟,并更好地估计时钟差异?
NTP 客户端发送一个带有本地时间 orig_time
的数据包,NTP 服务器在服务器时间 recv_time
收到该数据包。然后服务器在服务器时间 tx_time
回复,客户端在当地时间 dest_time
.
往返delay
计算为recv_time - orig_time + dest_time - tx_time
,时钟之间的偏移量为offset = (recv_time - orig_time + tx_time - dest_time) / 2
。
假设两个NTP数据包走的路径一致,正确的调整时间就是dest_time + offset
,相当于tx_time + delay/2
.
我在尝试将我的客户端计算机同步到 NTP 时间并检查它是否实际同步时找到了这个答案。基于@Vic,这意味着客户端时钟(与服务器 NTP 时钟相比)总是关闭:
dest_time + offset = tx_time + delay/2
dest_time - tx_time = delay/2 - offset
即
correction = delay/2 - offset
正如@Vic 所说,数据包可能采用不同的路由进出,但平均而言 correction
应该给你你的时钟偏移(我认为)。即使通过 time.nist.gov
与 os.system('w32tm /resync/nowait')
同步,我的计算机也总是以某种方式关闭 40 毫秒。欢迎评论!
这是我的代码。
import ntplib
from datetime import datetime, timezone
def get_ntp_time():
ntp_pool = ['pool.ntp.org', 'time.nist.gov']
def call_ntp(serverAddress):
call = ntplib.NTPClient()
return call.request(server, version=3)
for server in ntp_pool:
response = call_ntp(server)
print(f"server: {server}")
print(f"request packet sent (as LOCAL client time, orig_time): {datetime.fromtimestamp(response.orig_time, timezone.utc)}")
print(f"request packet received (as NTP server time, recv_time): {datetime.fromtimestamp(response.recv_time, timezone.utc)}")
print(f"response packet sent (as NTP server time, tx_time): {datetime.fromtimestamp(response.tx_time, timezone.utc)}")
print(f"response packet received (as LOCAL client time, dest_time): {datetime.fromtimestamp(response.dest_time, timezone.utc)}")
print(f'round trip duration: {response.delay} s')
print(f'* adjusted time, tx_time + delay/2: {datetime.fromtimestamp(response.tx_time + response.delay/2, timezone.utc)}')
print(f'* adjusted time, dest_time + offset: {datetime.fromtimestamp(response.dest_time + response.offset, timezone.utc)}')
print(f'correction to client: {response.delay/2 - response.offset} s\n')
# for attr in dir(response):
# if not attr .startswith('_'):
# print("response.%s = %r" % (attr, getattr(response, attr)))
print('-')
get_ntp_time()
回复:
server: pool.ntp.org
request packet sent (as LOCAL client time, orig_time): 2021-04-23 16:14:46.544797+00:00
request packet received (as NTP server time, recv_time): 2021-04-23 16:14:46.535852+00:00
response packet sent (as NTP server time, tx_time): 2021-04-23 16:14:46.535862+00:00
response packet received (as LOCAL client time, dest_time): 2021-04-23 16:14:46.579710+00:00
round trip duration: 0.03490257263183594 s
* adjusted time, tx_time + delay/2: 2021-04-23 16:14:46.553314+00:00
* adjusted time, dest_time + offset: 2021-04-23 16:14:46.553314+00:00
correction to client: 0.04384756088256836 s
-
server: time.nist.gov
request packet sent (as LOCAL client time, orig_time): 2021-04-23 16:14:46.642192+00:00
request packet received (as NTP server time, recv_time): 2021-04-23 16:14:46.641157+00:00
response packet sent (as NTP server time, tx_time): 2021-04-23 16:14:46.641158+00:00
response packet received (as LOCAL client time, dest_time): 2021-04-23 16:14:46.689054+00:00
round trip duration: 0.04686117172241211 s
* adjusted time, tx_time + delay/2: 2021-04-23 16:14:46.664588+00:00
* adjusted time, dest_time + offset: 2021-04-23 16:14:46.664588+00:00
correction to client: 0.0478968620300293 s
-
我发现前面的回答对dealy或offset(延迟的一半)计算有点迷惑。我想指出这一点。
原来,ntplib.py源,dest_timestamp(接收时间),orig_timestamp(发送时间)是本地(客户端)时间。 tx_timestamp(服务器发送时间)和recv_timestamp(服务器接收时间)是服务器时间。所以以下代码中的第一项表示数据包发送和接收差异,第二项表示服务器处理时间。
无论如何,调整后的时间可以这样计算 adjusted_time = response.tx_time + response.delay*0.5
@property
def delay(self):
"""round-trip delay"""
return ((self.dest_timestamp - self.orig_timestamp) -
(self.tx_timestamp - self.recv_timestamp))