java 使用 TimeTCPClient 从公共时间服务器获取时间
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/7081262/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Getting time from public time server using TimeTCPClient
提问by Cheok Yan Cheng
I try to use the following code to obtain time from public time server.
我尝试使用以下代码从公共时间服务器获取时间。
package aaa;
import java.util.Arrays;
import java.util.List;
import org.apache.commons.net.TimeTCPClient;
public final class Main
{
public static java.util.Date getNTPDate() {
List<String> hosts = Arrays.asList("0.pool.ntp.org");
for (String host : hosts) {
TimeTCPClient client = new TimeTCPClient();
// We want to timeout if a response takes longer than 5 seconds
client.setDefaultTimeout(5000);
try {
client.connect(host);
java.util.Date ntpDate = client.getDate();
client.disconnect();
// Just to be extra caution.
if (ntpDate != null) {
return ntpDate;
}
}
catch (java.net.SocketException exp) {
exp.printStackTrace();
}
catch (java.io.IOException exp) {
exp.printStackTrace();
}
}
return null;
}
public static final void main(String[] args)
{
System.out.println(getNTPDate());
}
}
However, all the time, I am getting java.net.ConnectException: Connection timed out: connect
然而,一直以来,我都得到 java.net.ConnectException: Connection timed out: connect
I had tried to google for several different time server. However, non of them work. I was wondering, is the problem lies on my code, or the server I choose?
我曾尝试用谷歌搜索几个不同的时间服务器。但是,它们都不起作用。我想知道,问题出在我的代码上,还是我选择的服务器上?
回答by Friek
NTP is a different protocol than the time protocol. NTP servers only talk over port UDP/123. Time servers use TCP/37 (which TimeTCPClient appears to implement correctly).
NTP 是与时间协议不同的协议。NTP 服务器仅通过端口 UDP/123 进行通信。时间服务器使用 TCP/37(TimeTCPClient 似乎正确实现)。
If you want to get a remote time, use an appropriate server (ntp.xs4all.nl
appears to be listening on the time port).
如果您想获得远程时间,请使用适当的服务器(ntp.xs4all.nl
似乎正在侦听时间端口)。
回答by marcolopes
You can use the correct approach:
您可以使用正确的方法:
import java.io.IOException;
import java.net.InetAddress;
import java.util.Date;
import org.apache.commons.net.ntp.NTPUDPClient;
import org.apache.commons.net.ntp.TimeInfo;
public final class PublicServerTime {
public static Date getNTPDate() {
String[] hosts = new String[]{
"ntp02.oal.ul.pt", "ntp04.oal.ul.pt",
"ntp.xs4all.nl"};
NTPUDPClient client = new NTPUDPClient();
// We want to timeout if a response takes longer than 5 seconds
client.setDefaultTimeout(5000);
for (String host : hosts) {
try {
InetAddress hostAddr = InetAddress.getByName(host);
System.out.println("> " + hostAddr.getHostName() + "/" + hostAddr.getHostAddress());
TimeInfo info = client.getTime(hostAddr);
Date date = new Date(info.getReturnTime());
return date;
}
catch (IOException e) {
e.printStackTrace();
}
}
client.close();
return null;
}
public static final void main(String[] args) {
System.out.println(getNTPDate());
}
回答by Oleksandr
Source:
来源:
public class NTPService {
private final static Logger logger = Logger.getLogger(NTPService.class);
private final static int TIMEOUT = 5000;
private final static List<String> hostList =
Arrays.asList("time.windows.com", "nl.pool.ntp.org");
private final NTPUDPClient client = new NTPUDPClient();
public NTPService() {
client.setDefaultTimeout(TIMEOUT);
}
public LocalDateTime getNTPDateTime() {
for (final String host : hostList) {
final LocalDateTime localDateTime = getNTPDateTime(host);
if (null != localDateTime) {
return localDateTime;
}
}
return null;
}
private LocalDateTime getNTPDateTime(final String host) {
try {
client.open();
return convertToLocalDateTime(
TimeStamp.getNtpTime(client.getTime(InetAddress.getByName(host))
.getReturnTime()).getTime());
} catch (final Exception exp) {
logger.warn(String.format("%s: failed to update NTP", host), exp);
return null;
} finally {
if (client.isOpen()) {
client.close();
}
}
}
private LocalDateTime convertToLocalDateTime(final long value) {
return LocalDateTime.ofInstant(Instant.ofEpochMilli(value),
ZoneId.systemDefault());
}
}
Usage:
用法:
System.out.println(DateTimeFormatter.ofPattern("yyyy.MM.dd HH:mm:ss").
format(new NTPService().getNTPDateTime()));