Moment.js se transforme en objet de date

696

En utilisant Moment.js, je ne peux pas transformer un objet moment correct en un objet date avec des fuseaux horaires. Je ne peux pas obtenir la bonne date.

Exemple:

var oldDate = new Date(),
    momentObj = moment(oldDate).tz("MST7MDT"),
    newDate = momentObj.toDate();
console.log("start date " + oldDate)
console.log("Format from moment with offset " + momentObj.format())
console.log("Format from moment without offset " + momentObj.utc().format())
console.log("(Date object) Time with offset " + newDate)
console.log("(Date object) Time without offset "+ moment.utc(newDate).toDate())
vadim.zhiltsov
la source
1
Quelle sortie attendez-vous et quelle sortie obtenez-vous?
Felix Kling
4
4 lignes pour obtenir la sortie: <code> (objet Date) Heure avec décalage jeu 01 août 2013 15:23:49 GMT + 0300 (Финляндия (лето)) </code> Mais le fuseau horaire doit être MST7MDT
vadim.zhiltsov
Wednesday 24th 2019, 12:47:48 amest-ce possible de convertir en 2019-04-23T19:17:48.000Z ? @ vadim.zhiltsov
Anupam Maurya
Les objets de date n'ont pas de fuseau horaire, ils ne sont qu'un décalage par rapport au 1970-01-01T00: 00: 00Z. Ainsi, lorsque vous appelez toDate , l'objet renvoyé a perdu les informations de fuseau horaire que vous avez attachées à l'objet moment avec .tz("MST7MDT"). C'est pourquoi des bibliothèques comme moment.tz existent, pour compléter la capacité de base de l'objet Date intégré qui ne comprend que l'UTC et le fuseau horaire de l'hôte, c'est tout.
RobG

Réponses:

1235

Utilisez ceci pour transformer un objet moment en un objet date:

Depuis http://momentjs.com/docs/#/displaying/as-javascript-date/

moment().toDate();

Rendements:

Tue Nov 04 2014 14:04:01 GMT-0600 (CST)
Chandrew
la source
11
@Spencer - Oui, il répond au titre, et toDatec'est en effet comment récupérer un Dateobjet à partir d'un moment. Mais le code dans le corps de la question pose des questions sur la conversion de fuseau horaire - ce qui Datene peut pas le faire. À moins que l'heure de la montagne ne soit en effet le fuseau horaire de l'utilisateur, je ne sais pas comment cela a répondu à la question.
Matt Johnson-Pint
1
@Matt cela dépend juste de la partie de la question que vous regardez. La majorité des gens recherchent sur Google et voient que ce titre correspond à leur question et votent pour la réponse qui répond au titre, pas au corps de la question. Cela pourrait expliquer pourquoi cela a le plus de votes positifs, même si cela n'aide pas techniquement le PO.
Spencer
14
Est-ce vraiment la bonne réponse? La question était de savoir comment transformer l'objet instant en date javascript mais avec TIMEZONE. Il revient toujours au fuseau horaire local lors du passage à l'objet de date javascript.
Unspeakable
1
Hé les gars, vérifiez ce lien momentjs.com/guides/#/warnings/js-date . Ceci est déconseillé et sera supprimé dans la prochaine version majeure.
gtzinos
3
@gtzinos ce que vous liez et faites référence est un problème et un scénario séparés, par exemple, passer une chaîne dans le constructeur du moment moment("12/12/2011")est l'endroit où vous obtiendriez ce message. Cela n'a rien à voir avec le fait d'aller du moment à ce jour objmoment().toDate()
btbJosh
51

Tant que vous avez initialisé le fuseau horaire avec les données des zones que vous souhaitez , votre code fonctionne comme prévu.

Vous convertissez correctement le moment en fuseau horaire, ce qui se reflète dans la deuxième ligne de sortie de momentObj.format().

Le passage à UTC ne fait pas que supprimer le décalage, il revient au fuseau horaire UTC. Si vous voulez faire cela, vous n'avez pas du tout besoin de l' .tz()appel d' origine . Tu pourrais juste faire moment.utc().

Peut-être que vous essayez simplement de changer la chaîne de format de sortie? Si c'est le cas, spécifiez simplement les paramètres que vous souhaitez pour la formatméthode:

momentObj.format("YYYY-MM-DD HH:mm:ss")

En ce qui concerne les dernières lignes de votre code - lorsque vous revenez à un Dateobjet en utilisant toDate(), vous abandonnez le comportement de moment.js et revenez au comportement de JavaScript. Un Dateobjet JavaScript sera toujours imprimé dans le fuseau horaire local de l'ordinateur sur lequel il s'exécute. Il n'y a rien de moment.js peut y faire.

Quelques autres petites choses:

  • Bien que le constructeur puisse en prendre un Date, il est généralement préférable de ne pas en utiliser un. Pour "maintenant", ne l'utilisez pas moment(new Date()). Au lieu de cela, utilisez simplement moment(). Les deux fonctionneront mais c'est inutilement redondant. Si vous analysez à partir d'une chaîne, passez cette chaîne directement dans moment. N'essayez pas de l'analyser en Datepremier. Vous trouverez que l'analyseur du moment est beaucoup plus fiable.

  • Les fuseaux horaires MST7MDTsont là pour des raisons de compatibilité descendante. Ils proviennent de fuseaux horaires de style POSIX, et seuls quelques-uns sont dans les données TZDB. Sauf si c'est absolument nécessaire, vous devez utiliser une clé telle que America/Denver.

Matt Johnson-Pint
la source
Merci Matt! Votre réponse a été utile. Comme vous l'avez mentionné sur l'utilisation de America / Denver au lieu de MST7MDT, existe-t-il une carte disponible pour ces mappages? J'utilise pas mal de fuseaux horaires comme CET, EET, EST5EDT, CST6CDT, PST8PDT.
monish001
est-il possible de convertir par exemple: "10:20 AM" (temps de chaîne obtenu à partir de moment (). format ('hh: mm A')) en objet Date ??
ram
2
@ram - 1) si vous avez un moment, utilisez simplement .toDate(). 2) N'utilisez pas de commentaires pour poser de nouvelles questions. C'est à cela que sert le gros bouton "Poser une question" .
Matt Johnson-Pint
22

.toDate n'a pas vraiment fonctionné pour moi, alors, voici ce que j'ai fait:

futureStartAtDate = new Date(moment().locale("en").add(1, 'd').format("MMM DD, YYYY HH:MM"))

J'espère que cela t'aides

Mawaheb
la source
2
Cette réponse ne répond pas à la question. Le code est une façon d'écrire de longue haleine moment().add(1, 'd').toDate().
RobG
12

Puisque momentjs n'a aucun contrôle sur l'objet de date javascript, j'ai trouvé un moyen de contourner cela.

const currentTime = new Date();    
const convertTime = moment(currentTime).tz(timezone).format("YYYY-MM-DD HH:mm:ss");
const convertTimeObject = new Date(convertTime);

Cela vous donnera un objet de date javascript avec l'heure convertie

Yasith Prabuddhaka
la source
2
C'est la seule bonne réponse qui répond directement à la question.
Anish Sana
1
C'est exactement ce que je voulais. Je m'attendais à ce que les dates natives représentent correctement les fuseaux horaires, mais j'avais malheureusement tort.
mklbtz
1
Le format "AAAA-MM-JJ HH: mm: ss" n'est pas pris en charge par Safari, le résultat est donc nul . Le format doit être "AAAA-MM-JJTHH: mm: ss" (utilisez un format pris en charge par ECMAScript, un "T" entre les parties date et heure).
RobG
4

J'avais besoin d'avoir des informations de fuseau horaire dans ma chaîne de date. J'utilisais à l'origine moment.tz(dateStr, 'America/New_York').toString();mais j'ai ensuite commencé à obtenir des erreurs concernant la réintroduction de cette chaîne dans l'instant.

J'ai essayé moment.tz(dateStr, 'America/New_York').toDate();mais j'ai perdu les informations de fuseau horaire dont j'avais besoin.

La seule solution qui a renvoyé une chaîne de date utilisable avec un fuseau horaire pouvant être réinjecté dans l'instant étaitmoment.tz(dateStr, 'America/New_York').format();

chovy
la source
4
let dateVar = moment('any date value');
let newDateVar = dateVar.utc().format();

Agréable et propre!!!!

Emerson Bottero
la source
C'était la seule solution ici dans mon cas qui a fonctionné pour avoir un format utc. Merci
Luis Febro
3

Pour convertir n'importe quelle date, par exemple utc:

moment( moment().utc().format( "YYYY-MM-DD HH:mm:ss" )).toDate()
kizoso
la source
2
Cela m'a vraiment sauvé la journée!
HV Sharma
Cette réponse est fausse. Il applique le décalage de fuseau horaire deux fois: moment().utc()renvoie des valeurs pour UTC, puis .format( "YYYY-MM-DD HH:mm:ss" )renvoie une chaîne qui a été définie sur UTC sans décalage de fuseau horaire et est donc analysée comme locale. Il ne correspond pas à un format de moment par défaut, il est donc analysé par l'analyseur intégré. Il ne correspond pas non plus aux formats pris en charge par ECMAScript, donc l'analyse dépend de l'implémentation. Quoi qu'il en soit, il est analysé comme local, de sorte que le décalage de fuseau horaire est appliqué à nouveau lors de la création de la valeur d'heure de la date.
RobG
3

La question est un peu obscure. Je ferai de mon mieux pour expliquer cela. Vous devez d'abord comprendre comment utiliser le fuseau horaire . Selon cette réponse ici, TypeError: moment (). Tz n'est pas une fonction , vous devez importer le moment à partir du moment-fuseau horaire au lieu du moment par défaut (bien sûr, vous devrez d'abord npm installer le moment-fuseau horaire!). Par souci de clarté,

const moment=require('moment-timezone')//import from moment-timezone

Maintenant, pour utiliser la fonction de fuseau horaire, utilisez moment.tz ("date_string / moment ()", "time_zone") (visitez https://momentjs.com/timezone/ pour plus de détails). Cette fonction renvoie un objet moment avec un fuseau horaire particulier. Par souci de clarté,

var newYork= moment.tz("2014-06-01 12:00", "America/New_York");/*this code will consider NewYork as the timezone.*/

Maintenant, lorsque vous essayez de convertir newYork (l'objet moment) avec moment's toDate () (conversion au format ISO 8601), vous obtiendrez l'heure de Greenwich, au Royaume-Uni. Pour plus de détails, consultez cet article https://www.nhc.noaa.gov/aboututc.shtml , sur UTC. Cependant, si vous voulez juste votre heure locale dans ce format (heure de New York, selon cet exemple), ajoutez simplement la méthode .utc (true) , avec l' argument true , à votre objet moment. Par souci de clarté,

newYork.toDate()//will give you the Greenwich ,UK, time.

newYork.utc(true).toDate()//will give you the local time. according to the moment.tz method arg we specified above, it is 12:00.you can ofcourse change this by using moment()

En bref, moment.tz considère le fuseau horaire que vous spécifiez et compare votre heure locale avec l'heure de Greenwich pour vous donner un résultat. J'espère que cela a été utile.

Vijay Joshua Nadar
la source
2

moment a mis à jour le js lib à partir du 06/2018.

var newYork    = moment.tz("2014-06-01 12:00", "America/New_York");
var losAngeles = newYork.clone().tz("America/Los_Angeles");
var london     = newYork.clone().tz("Europe/London");

newYork.format();    // 2014-06-01T12:00:00-04:00
losAngeles.format(); // 2014-06-01T09:00:00-07:00
london.format();     // 2014-06-01T17:00:00+01:00

si vous avez la liberté d'utiliser Angular5 +, mieux vaut utiliser la fonction datePipe ici que la fonction de fuseau horaire ici. Je dois utiliser moment.js car mon projet se limite à Angular2 uniquement.

Feng Zhang
la source
1

essayez (sans formatétape)

new Date(moment())

Kamil Kiełczewski
la source
new Date(moment())est équivalent à new Date(). Le fuseau horaire n'est défini que pour d .
RobG