I am making an app in which I want to get the current time from internet.
我正在制作一个应用程序,我希望从互联网获取当前时间。
I know how to get the time from the device using System.currentTimeMillis
, and even after searching a lot, I did not get any clue about how to get it from internet.
我知道如何使用System.currentTimeMillis从设备中获取时间,即使经过大量搜索,我也没有得到任何关于如何从互联网上获取它的线索。
6 个解决方案
#1
17
You can get time from internet time servers using the below program
您可以使用以下程序从互联网时间服务器获得时间
import java.io.IOException;
import org.apache.commons.net.time.TimeTCPClient;
public final class GetTime {
public static final void main(String[] args) {
try {
TimeTCPClient client = new TimeTCPClient();
try {
// Set timeout of 60 seconds
client.setDefaultTimeout(60000);
// Connecting to time server
// Other time servers can be found at : http://tf.nist.gov/tf-cgi/servers.cgi#
// Make sure that your program NEVER queries a server more frequently than once every 4 seconds
client.connect("time.nist.gov");
System.out.println(client.getDate());
} finally {
client.disconnect();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
1.You would need Apache Commons Net library for this to work. Download the library and add to your project build path.
你需要Apache Commons Net库才能工作。下载库并添加到项目构建路径。
(Or you can also use the trimmed Apache Commons Net Library here : https://www.dropbox.com/s/bjxjv7phkb8xfhh/commons-net-3.1.jar. This is enough to get time from internet )
(或者你也可以在这里使用修剪过的Apache Commons Net Library:https://www.dropbox.com/s/bjxjv7phkb8xfhh/commons-net-3.1.jar。这足以从互联网上获取时间)
2.Run the program. You will get the time printed on your console.
2.运行程序。您将在控制台上打印时间。
#2
7
Here is a method that i have created for you you can use this in your code
这是我为您创建的方法,您可以在代码中使用它
public String getTime() {
try{
//Make the Http connection so we can retrieve the time
HttpClient httpclient = new DefaultHttpClient();
// I am using yahoos api to get the time
HttpResponse response = httpclient.execute(new
HttpGet("http://developer.yahooapis.com/TimeService/V1/getTime?appid=YahooDemo"));
StatusLine statusLine = response.getStatusLine();
if(statusLine.getStatusCode() == HttpStatus.SC_OK){
ByteArrayOutputStream out = new ByteArrayOutputStream();
response.getEntity().writeTo(out);
out.close();
// The response is an xml file and i have stored it in a string
String responseString = out.toString();
Log.d("Response", responseString);
//We have to parse the xml file using any parser, but since i have to
//take just one value i have deviced a shortcut to retrieve it
int x = responseString.indexOf("<Timestamp>");
int y = responseString.indexOf("</Timestamp>");
//I am using the x + "<Timestamp>" because x alone gives only the start value
Log.d("Response", responseString.substring(x + "<Timestamp>".length(),y) );
String timestamp = responseString.substring(x + "<Timestamp>".length(),y);
// The time returned is in UNIX format so i need to multiply it by 1000 to use it
Date d = new Date(Long.parseLong(timestamp) * 1000);
Log.d("Response", d.toString() );
return d.toString() ;
} else{
//Closes the connection.
response.getEntity().getContent().close();
throw new IOException(statusLine.getReasonPhrase());
}
}catch (ClientProtocolException e) {
Log.d("Response", e.getMessage());
}catch (IOException e) {
Log.d("Response", e.getMessage());
}
return null;
}
#3
1
You will need to have access to a webservice that provides current time in XML or JSON format.
您需要访问以XML或JSON格式提供当前时间的Web服务。
If you don't find such type of service, you could parse the time from a web page, like http://www.timeanddate.com/worldclock/, or host your own time service on a server using a simple PHP page for example.
如果您没有找到这种类型的服务,您可以从网页(如http://www.timeanddate.com/worldclock/)解析时间,或者使用简单的PHP页面在服务器上托管您自己的时间服务例。
Check out JSoup for the parsing of HTML pages.
查看JSoup以解析HTML页面。
#4
1
I think the best solution is to use SNTP, in particular the SNTP client code from Android itself, e.g.: http://grepcode.com/file/repository.grepcode.com/java/ext/com.google.android/android/4.1.1_r1/android/net/SntpClient.java/
我认为最好的解决方案是使用SNTP,特别是Android本身的SNTP客户端代码,例如:http://grepcode.com/file/repository.grepcode.com/java/ext/com.google.android/android/ 4.1.1_r1 /安卓/ NET / SntpClient.java /
I believe Android uses SNTP for automatic date/time updates when a cell network is not available (e.g. wifi tablets).
我相信当无法使用手机网络时,Android会使用SNTP进行自动日期/时间更新(例如wifi平板电脑)。
I think it is better then the other solutions because it uses SNTP/NTP rather then the Time protocol (RFC 868) used by the Apache TimeTCPClient. I don't know anything bad about RFC 868, but NTP is newer and seems to have superceeded it and is more widely used. I believe that Android devices that don't have cellular uses NTP.
我认为它比其他解决方案更好,因为它使用SNTP / NTP而不是Apache TimeTCPClient使用的时间协议(RFC 868)。我对RFC 868一无所知,但NTP更新,似乎已经超越它并且被更广泛地使用。我相信没有手机的Android设备使用NTP。
Also, because it uses sockets. Some of the solutions proposed use HTTP so they will lose something in their accuracy.
此外,因为它使用套接字。建议的一些解决方案使用HTTP,因此它们将失去准确性。
#5
1
Nothing from the above worked from me. This is what I ended up with (with Volley);
This example also converts to another timezone.
上面没有任何内容对我有用。这就是我最终的结果(与Volley一起);此示例还转换为另一个时区。
Long time = null;
RequestQueue queue = Volley.newRequestQueue(this);
String url ="http://www.timeapi.org/utc/now";
StringRequest stringRequest = new StringRequest(Request.Method.GET, url,
new Response.Listener<String>() {
@Override
public void onResponse(String response) {
try {
SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
simpleDateFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
Date date = simpleDateFormat.parse(response);
TimeZone tz = TimeZone.getTimeZone("Israel");
SimpleDateFormat destFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
destFormat.setTimeZone(tz);
String result = destFormat.format(date);
Log.d(TAG, "onResponse: " + result.toString());
} catch (ParseException e) {
e.printStackTrace();
}
}
}, new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError error) {
Log.w(TAG, "onErrorResponse: "+ error.getMessage());
}
});
queue.add(stringRequest);
return time;
Import Volley in gradle:
在gradle中导入Volley:
compile 'com.android.volley:volley:1.0.0'
#6
0
If you don't care for millisecond accuracy, and if you are already using google firebase or don't mind using it (they provide a free tier), check this out: https://firebase.google.com/docs/database/android/offline-capabilities#clock-skew
如果您不关心毫秒精度,并且您已经在使用谷歌firebase或不介意使用它(它们提供免费套餐),请查看以下内容:https://firebase.google.com/docs/database /安卓/离线功能#时钟偏斜
Basically, firebase database has a field that provides offset value between the device time and the firebase server time. You can use this offset to get the current time.
基本上,firebase数据库有一个字段,它提供设备时间和firebase服务器时间之间的偏移值。您可以使用此偏移量来获取当前时间。
DatabaseReference offsetRef = FirebaseDatabase.getInstance().getReference(".info/serverTimeOffset");
offsetRef.addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(DataSnapshot snapshot) {
double offset = snapshot.getValue(Double.class);
double estimatedServerTimeMs = System.currentTimeMillis() + offset;
}
@Override
public void onCancelled(DatabaseError error) {
System.err.println("Listener was cancelled");
}
});
As I said, it will be inaccurate based on network latency.
正如我所说,基于网络延迟,它将是不准确的。
#1
17
You can get time from internet time servers using the below program
您可以使用以下程序从互联网时间服务器获得时间
import java.io.IOException;
import org.apache.commons.net.time.TimeTCPClient;
public final class GetTime {
public static final void main(String[] args) {
try {
TimeTCPClient client = new TimeTCPClient();
try {
// Set timeout of 60 seconds
client.setDefaultTimeout(60000);
// Connecting to time server
// Other time servers can be found at : http://tf.nist.gov/tf-cgi/servers.cgi#
// Make sure that your program NEVER queries a server more frequently than once every 4 seconds
client.connect("time.nist.gov");
System.out.println(client.getDate());
} finally {
client.disconnect();
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
1.You would need Apache Commons Net library for this to work. Download the library and add to your project build path.
你需要Apache Commons Net库才能工作。下载库并添加到项目构建路径。
(Or you can also use the trimmed Apache Commons Net Library here : https://www.dropbox.com/s/bjxjv7phkb8xfhh/commons-net-3.1.jar. This is enough to get time from internet )
(或者你也可以在这里使用修剪过的Apache Commons Net Library:https://www.dropbox.com/s/bjxjv7phkb8xfhh/commons-net-3.1.jar。这足以从互联网上获取时间)
2.Run the program. You will get the time printed on your console.
2.运行程序。您将在控制台上打印时间。
#2
7
Here is a method that i have created for you you can use this in your code
这是我为您创建的方法,您可以在代码中使用它
public String getTime() {
try{
//Make the Http connection so we can retrieve the time
HttpClient httpclient = new DefaultHttpClient();
// I am using yahoos api to get the time
HttpResponse response = httpclient.execute(new
HttpGet("http://developer.yahooapis.com/TimeService/V1/getTime?appid=YahooDemo"));
StatusLine statusLine = response.getStatusLine();
if(statusLine.getStatusCode() == HttpStatus.SC_OK){
ByteArrayOutputStream out = new ByteArrayOutputStream();
response.getEntity().writeTo(out);
out.close();
// The response is an xml file and i have stored it in a string
String responseString = out.toString();
Log.d("Response", responseString);
//We have to parse the xml file using any parser, but since i have to
//take just one value i have deviced a shortcut to retrieve it
int x = responseString.indexOf("<Timestamp>");
int y = responseString.indexOf("</Timestamp>");
//I am using the x + "<Timestamp>" because x alone gives only the start value
Log.d("Response", responseString.substring(x + "<Timestamp>".length(),y) );
String timestamp = responseString.substring(x + "<Timestamp>".length(),y);
// The time returned is in UNIX format so i need to multiply it by 1000 to use it
Date d = new Date(Long.parseLong(timestamp) * 1000);
Log.d("Response", d.toString() );
return d.toString() ;
} else{
//Closes the connection.
response.getEntity().getContent().close();
throw new IOException(statusLine.getReasonPhrase());
}
}catch (ClientProtocolException e) {
Log.d("Response", e.getMessage());
}catch (IOException e) {
Log.d("Response", e.getMessage());
}
return null;
}
#3
1
You will need to have access to a webservice that provides current time in XML or JSON format.
您需要访问以XML或JSON格式提供当前时间的Web服务。
If you don't find such type of service, you could parse the time from a web page, like http://www.timeanddate.com/worldclock/, or host your own time service on a server using a simple PHP page for example.
如果您没有找到这种类型的服务,您可以从网页(如http://www.timeanddate.com/worldclock/)解析时间,或者使用简单的PHP页面在服务器上托管您自己的时间服务例。
Check out JSoup for the parsing of HTML pages.
查看JSoup以解析HTML页面。
#4
1
I think the best solution is to use SNTP, in particular the SNTP client code from Android itself, e.g.: http://grepcode.com/file/repository.grepcode.com/java/ext/com.google.android/android/4.1.1_r1/android/net/SntpClient.java/
我认为最好的解决方案是使用SNTP,特别是Android本身的SNTP客户端代码,例如:http://grepcode.com/file/repository.grepcode.com/java/ext/com.google.android/android/ 4.1.1_r1 /安卓/ NET / SntpClient.java /
I believe Android uses SNTP for automatic date/time updates when a cell network is not available (e.g. wifi tablets).
我相信当无法使用手机网络时,Android会使用SNTP进行自动日期/时间更新(例如wifi平板电脑)。
I think it is better then the other solutions because it uses SNTP/NTP rather then the Time protocol (RFC 868) used by the Apache TimeTCPClient. I don't know anything bad about RFC 868, but NTP is newer and seems to have superceeded it and is more widely used. I believe that Android devices that don't have cellular uses NTP.
我认为它比其他解决方案更好,因为它使用SNTP / NTP而不是Apache TimeTCPClient使用的时间协议(RFC 868)。我对RFC 868一无所知,但NTP更新,似乎已经超越它并且被更广泛地使用。我相信没有手机的Android设备使用NTP。
Also, because it uses sockets. Some of the solutions proposed use HTTP so they will lose something in their accuracy.
此外,因为它使用套接字。建议的一些解决方案使用HTTP,因此它们将失去准确性。
#5
1
Nothing from the above worked from me. This is what I ended up with (with Volley);
This example also converts to another timezone.
上面没有任何内容对我有用。这就是我最终的结果(与Volley一起);此示例还转换为另一个时区。
Long time = null;
RequestQueue queue = Volley.newRequestQueue(this);
String url ="http://www.timeapi.org/utc/now";
StringRequest stringRequest = new StringRequest(Request.Method.GET, url,
new Response.Listener<String>() {
@Override
public void onResponse(String response) {
try {
SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss");
simpleDateFormat.setTimeZone(TimeZone.getTimeZone("UTC"));
Date date = simpleDateFormat.parse(response);
TimeZone tz = TimeZone.getTimeZone("Israel");
SimpleDateFormat destFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
destFormat.setTimeZone(tz);
String result = destFormat.format(date);
Log.d(TAG, "onResponse: " + result.toString());
} catch (ParseException e) {
e.printStackTrace();
}
}
}, new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError error) {
Log.w(TAG, "onErrorResponse: "+ error.getMessage());
}
});
queue.add(stringRequest);
return time;
Import Volley in gradle:
在gradle中导入Volley:
compile 'com.android.volley:volley:1.0.0'
#6
0
If you don't care for millisecond accuracy, and if you are already using google firebase or don't mind using it (they provide a free tier), check this out: https://firebase.google.com/docs/database/android/offline-capabilities#clock-skew
如果您不关心毫秒精度,并且您已经在使用谷歌firebase或不介意使用它(它们提供免费套餐),请查看以下内容:https://firebase.google.com/docs/database /安卓/离线功能#时钟偏斜
Basically, firebase database has a field that provides offset value between the device time and the firebase server time. You can use this offset to get the current time.
基本上,firebase数据库有一个字段,它提供设备时间和firebase服务器时间之间的偏移值。您可以使用此偏移量来获取当前时间。
DatabaseReference offsetRef = FirebaseDatabase.getInstance().getReference(".info/serverTimeOffset");
offsetRef.addValueEventListener(new ValueEventListener() {
@Override
public void onDataChange(DataSnapshot snapshot) {
double offset = snapshot.getValue(Double.class);
double estimatedServerTimeMs = System.currentTimeMillis() + offset;
}
@Override
public void onCancelled(DatabaseError error) {
System.err.println("Listener was cancelled");
}
});
As I said, it will be inaccurate based on network latency.
正如我所说,基于网络延迟,它将是不准确的。