Comment obtenir UTC Timestamp en JavaScript?
lors de l'écriture d'une application web, il est logique de stocker (côté serveur) toutes les datetimes dans le DB comme UTC timestamps.
j'ai été étonné quand j'ai remarqué que vous ne pouviez pas nativement faire grand chose en termes de manipulation du fuseau horaire en JavaScript.
j'ai un peu prolongé l'objet Date. Cette fonction a un sens? En gros, chaque fois que j'envoie quelque chose au serveur, ça va être un timestamp formaté avec ceci fonction...
pouvez-vous voir des problèmes majeurs ici? Ou peut-être une solution sous un autre angle?
Date.prototype.getUTCTime = function(){
return new Date(
this.getUTCFullYear(),
this.getUTCMonth(),
this.getUTCDate(),
this.getUTCHours(),
this.getUTCMinutes(),
this.getUTCSeconds()
).getTime();
}
il me semble juste un peu alambiqué. Et je ne suis pas sûr de la performance non plus.
15 réponses
-
les Dates construites de cette façon utilisent le fuseau horaire local, ce qui rend la date construite incorrecte. Définir le fuseau horaire d'un objet date est de le construire à partir d'une chaîne de date qui inclut le fuseau horaire. (J'ai eu de la difficulté à obtenir que cela fonctionne dans un navigateur Android plus ancien.)
-
notez que
getTime()
renvoie des millisecondes, pas des secondes simples.
pour un UTC/timestamp Unix, ce qui suit devrait suffire:
Math.floor((new Date()).getTime() / 1000)
il va prendre en compte le décalage du fuseau horaire actuel dans le résultat. Pour une représentation de chaîne, David Ellis' réponse œuvres.
pour clarifier:
new Date(Y, M, D, h, m, s)
cette entrée est traitée comme heure locale . Si UTC est passé, les résultats seront différents. Observer (je suis au GMT +02: 00 en ce moment, et il est 07: 50):
> var d1 = new Date();
> d1.toUTCString();
"Sun, 18 Mar 2012 05:50:34 GMT" // two hours less than my local time
> Math.floor(d1.getTime()/ 1000)
1332049834
> var d2 = new Date( d1.getUTCFullYear(), d1.getUTCMonth(), d1.getUTCDate(), d1.getUTCHours(), d1.getUTCMinutes(), d1.getUTCSeconds() );
> d2.toUTCString();
"Sun, 18 Mar 2012 03:50:34 GMT" // four hours less than my local time, and two hours less than the original time - because my GMT+2 input was interpreted as GMT+0!
> Math.floor(d2.getTime()/ 1000)
1332042634
il est également à noter que getUTCDate()
ne peut être remplacé par getUTCDay()
. C'est parce que getUTCDate()
retourne le jour du mois ; alors que getUTCDay()
retourne le jour de la semaine .
vous pouvez également le faire en utilisant getTimezoneOffset et getTime,
x = new Date()
var UTCseconds = (x.getTime() + x.getTimezoneOffset()*60*1000)/1000;
console.log("UTCseconds", UTCseconds)
Oui, vous n'avez pas besoin de faire beaucoup; en supposant que je vous comprends correctement, vous voulez juste le toUTCString
méthode .
var UTCstring = (new Date()).toUTCString();
console.log('UTCstring', UTCstring);
cependant, rappelez-vous que les valeurs de date que vous obtenez sont basées sur l'horloge de la machine du client, pas votre serveur. Si vous avez besoin de valeurs précises pour ces dates (par exemple, pour commander correctement quand telle ou telle action a été faite par rapport à l'action d'un autre utilisateur), vous ne peut pas se fier à la bibliothèque de date côté client, de toute façon, et vous devez calculer les dates côté serveur basé sur quand le client vous a contacté.
rappelez-vous aussi que fondamentalement tout votre code côté client peut être modifié par le client et les valeurs malveillantes retournées à la place, vous ne pouvez garantir le code sur le côté serveur -- traiter le côté client comme un attaquant possible.
vous n'avez généralement pas besoin de faire beaucoup de" manipulation du fuseau horaire " du côté du client. En règle générale, j'essaie de stocker et de travailler avec des dates UTC, sous la forme de ticks
ou nombre de millisecondes depuis minuit du 1er janvier 1970 ."Cela simplifie vraiment le stockage, le tri, le calcul des offsets, et surtout, vous dispense des maux de tête des réglages "D'heure D'été". Voici un petit code JavaScript que j'utilise.
pour obtenir le heure UTC actuelle:
function getCurrentTimeUTC()
{
//RETURN:
// = number of milliseconds between current UTC time and midnight of January 1, 1970
var tmLoc = new Date();
//The offset is in minutes -- convert it to ms
return tmLoc.getTime() + tmLoc.getTimezoneOffset() * 60000;
}
alors ce dont vous avez généralement besoin est de formater la date/heure pour l'utilisateur final pour leur locale fuseau horaire et format. Ce qui suit traite de toutes les complexités des formats de date et d'heure sur l'ordinateur client:
function formatDateTimeFromTicks(nTicks)
{
//'nTicks' = number of milliseconds since midnight of January 1, 1970
//RETURN:
// = Formatted date/time
return new Date(nTicks).toLocaleString();
}
function formatDateFromTicks(nTicks)
{
//'nTicks' = number of milliseconds since midnight of January 1, 1970
//RETURN:
// = Formatted date
return new Date(nTicks).toLocaleDateString();
}
function formatTimeFromTicks(nTicks)
{
//'nTicks' = number of milliseconds since midnight of January 1, 1970
//RETURN:
// = Formatted time
return new Date(nTicks).toLocaleTimeString();
}
ainsi l'exemple suivant:
var ticks = getCurrentTimeUTC(); //Or get it from the server
var __s = "ticks=" + ticks +
", DateTime=" + formatDateTimeFromTicks(ticks) +
", Date=" + formatDateFromTicks(ticks) +
", Time=" + formatTimeFromTicks(ticks);
document.write("<span>" + __s + "</span>");
Returns the following (for my U. S. English locale):
tics=1409103400661, DateTime= 8/26/2014 6:36: 40 PM, Date = 8/26/2014, Heure=6: 36 :40 PM
en fait, je pense que les valeurs de Date dans js sont bien meilleures que les objets C# DateTime. Les objets C# DateTime ont une propriété Kind, mais pas de fuseau horaire sous-jacent strict en tant que tel, et les conversions de fuseau horaire sont difficiles à suivre si vous convertissez entre deux heures non UTC et non locales. Dans js, toutes les valeurs de Date ont une valeur UTC sous-jacente qui est transmise et connue indépendamment des conversions offest ou fuseau horaire que vous faites. Ma plus grande plainte au sujet de L'objet Date est le nombre de comportements non définis que les responsables de la mise en œuvre du navigateur ont choisi d'inclure, ce qui peut confondre les personnes qui attaquent les dates dans js avec trial and error plutôt que de lire les spécifications. En utilisant quelque chose comme iso8601.js résout ce comportement variable en définissant une seule implémentation de L'objet Date.
par défaut, la spécification dit que vous pouvez créer des dates avec un format de date ISO 8601 étendu comme
var someDate = new Date('2010-12-12T12:00Z');
donc vous pouvez inférer l'heure UTC exacte de cette façon.
lorsque vous voulez renvoyer la valeur de la Date au serveur que vous appelleriez
someDate.toISOString();
ou si vous préférez travailler avec un horodatage milliseconde (nombre de millisecondes à partir du 1er janvier 1970 UTC)
someDate.getTime();
la norme ISO 8601 est une norme. Vous ne pouvez pas être confus sur ce que signifie une chaîne de date si vous incluez la date offset. Ce que cela signifie pour vous en tant que développeur est que vous n'ont jamais à traiter avec le local conversions de temps vous-même . Les valeurs de l'heure locale existent uniquement pour le bénéfice de l'utilisateur, et les valeurs de date par défaut s'affichent dans leur heure locale. Toutes les manipulations locales de temps vous permettent d'afficher quelque chose de sensible à l'utilisateur et de convertir des chaînes à partir de l'entrée de l'utilisateur. C'est une bonne pratique de passer à UTC dès que vous le pouvez, et l'objet Date js rend cela assez insignifiant.
du côté négatif, il n'y a pas beaucoup de place pour forcer le fuseau horaire ou locale pour le client (que je connais), ce qui peut être ennuyeux pour les paramètres spécifiques au site Web, mais je suppose que le raisonnement derrière ceci est que c'est une configuration utilisateur qui ne devrait pas être touchée.
donc, en résumé, la raison pour laquelle il n'y a pas beaucoup de support natif pour la manipulation des fuseaux horaires est que vous ne voulez tout simplement pas le faire.
la façon la plus facile d'obtenir du temps UTC dans un format conventionnel est la suivante:
new Date().toISOString()
"2016-06-03T23:15:33.008Z"
j'utilise ce qui suit:
Date.prototype.getUTCTime = function(){
return this.getTime()-(this.getTimezoneOffset()*60000);
};
une fois cette méthode définie, vous pouvez faire:
var utcTime = new Date().getUTCTime();
si vous voulez un one liner , le UTC Unix Timestamp peut être créé en JavaScript comme:
var currentUnixTimestap = ~~(+new Date() / 1000);
cela tiendra compte du fuseau horaire du système. C'est essentiellement le temps écoulé en secondes depuis l'époque.
Comment cela fonctionne:
- créer l'objet date:
new Date()
. - convertir en timestamp en ajoutant
unary +
avant création d'objet pour le convertir entimestamp integer
. :+new Date()
. - convertir millisecondes en secondes:
+new Date() / 1000
- utiliser double tildes pour arrondir la valeur à Entier. :
~~(+new Date())
je pense que c'est une meilleure solution
// UTC milliseconds
new Date(Date.now()+(new Date().getTimezoneOffset()*60000)).getTime()
// UTC seconds
new Date(Date.now()+(new Date().getTimezoneOffset()*60000)).getTime()/1000|0
depuis new Date().toUTCString()
renvoie une chaîne comme "Wed, 11 Oct 2017 09:24:41 GMT"
vous pouvez trancher les 3 derniers caractères et passer la chaîne tranchée à new Date()
:
new Date()
// Wed Oct 11 2017 11:34:33 GMT+0200 (CEST)
new Date(new Date().toUTCString().slice(0, -3))
// Wed Oct 11 2017 09:34:33 GMT+0200 (CEST)
EDIT: le code ci-dessous ne fonctionne pas. J'ai toujours supposé que nouvelle Date ().getTime () renvoie le nombre de secondes depuis le 1er janvier 1970 dans le fuseau horaire actuel. Ce n'est pas le cas: getTime() renvoie le nombre de secondes dans UTC. Donc, le code ci-dessous fait un surajustement Brutal. Merci tout le monde!]
tout d'Abord, merci pour votre fantastique idées. Je suppose que ma question avait le mauvais titre... il aurait dû être " Get the UTC Unix Timestamp for une date existant".
donc, si j'ai un objet date:
var d = new Date(2009,01,31)
je cherchais une fonction qui me dirait"L'horodatage Unix UTC".
Cette fonction semble être le vrai truc:
Date.prototype.getUTCUnixTime = function (){
return Math.floor( new Date(
this.getUTCFullYear(),
this.getUTCMonth(),
this.getUTCDate(),
this.getUTCHours(),
this.getUTCMinutes(),
this.getUTCSeconds()
).getTime() / 1000);
}
notez qu'il fonctionne sur "ceci" cela signifie que je peux faire:
var n = new Date(2008,10,10)
...
...
n.getUTCUnixTime();
et obtenir le nombre de secondes depuis le 1er janvier 1970 dans le temps Unix. Droit?
C'est un peu fou, pour moi, que Javascript stocke tout dans UTC times, mais ensuite pour obtenir ce numéro, je dois créer un nouvel objet Date passant les getters UTC individuels et finalement appeler getTime() pour ça...
Merc.
je suis étonné de la complexité de cette question.
ce sont tous identiques, et leurs valeurs entières tous = = = temps D'époque: d
console.log((new Date()).getTime() / 1000, new Date().valueOf() / 1000, (new Date() - new Date().getTimezoneOffset() * 60 * 1000) / 1000);
ne me croyez pas, caisse: http://www.epochconverter.com /
je tiens à préciser cette nouvelle Date().getTime () renvoie en fait une valeur UTC, donc c'est une façon très utile de stocker et de gérer les dates d'une manière qui est agnostique aux temps localisés.
en d'autres termes, ne vous embêtez pas avec toutes les fonctions javascript UTC. À la place, utilisez la Date.getTime ().
plus d'informations sur l'explication est ici: Si javascript "(new Date()).getTime () " est exécuté à partir de 2 fuseaux horaires différents.
je pense que c'est ce que vous attendez...
var currTimestamp = Date.now(), //1482905176396
utcDateString = (new Date(currTimestamp)).toUTCString(); //"Wed, 28 Dec 2016 06:06:50 GMT"
maintenant,
new Date(utcDateString).getTime(); //This will give you UTC Timestamp in JavaScript
cela retournera l'horodatage dans UTC:
var utc = new Date(new Date().toUTCString()).getTime();