2010-02-04 3 views
2

J'ai un service WCF qui reçoit des enregistrements avec des valeurs datetime et les enregistre dans un SQL Azure db, en utilisant Entity Framework 3.5 SP1. Exécuter localement, les enregistrements s'enregistrés dans la base de données, tout est bienWCF to Entity Framework convertit mon datetime en heure locale - comment arrêter?

Cependant, mon hébergement IIS est dans un fuseau horaire différent. Lorsque je télécharge le site là-bas et appelle le même service (avec exactement la même chaîne de connexion, à la base de données Azure SQL), les enregistrements sont toujours enregistrés, mais le temps a reculé de 5 heures.

J'ai vérifié Fiddler, pour regarder les données sortir, et il est à mon heure locale. J'ai utilisé le même service à l'intérieur de l'hébergement Azure, et cela a aussi bien fonctionné. J'ai les mêmes données allant à un autre service WCF sur le même hôte enregistré avec Linq2SQL, et cela économise bien. La seule différence est alors Entity Framework - Je devine que mes informations de fuseau horaire (GMT) sont envoyées avec le datetime, et ainsi quand le serveur dans le temps de Eastern Seaboard le reçoit, il le convertit à l'heure locale, 5 heures plus tôt.

Dans un sens, c'est précis, parce que pour le moment (13:48), il est 5 heures earler - 08:48, mais ce n'est pas ce que je veux enregistrer dans la base de données, je veux enregistrer 13h48. Comme je l'ai demandé, donc il est logique quand je l'interroger

Ceci est probablement très simple, et tout le monde sait la réponse, mais je suis un peu perplexe. J'apprécierais vraiment que quelqu'un puisse me diriger dans la bonne direction.

merci beaucoup

Toby

+0

J'ai une solution de contournement qui semble faire l'affaire -. définir mon datetime original, quand je crée sur le client, comme Utc. Ma classe d'aide sur le serveur le spécifie également comme Utc. De cette façon, la bonne date est enregistrée Cependant, cela pourrait être juste une coïncidence, car GMT est UTC - cela pourrait ne pas fonctionner aussi bien dans 3 mois lorsque nous passerons à l'heure d'été Serait une conversion à "ToLocaltime()" travailler alors? Hmm, dunno idées plus, de prendre le temps d'économiser correctement? – TobyEvans

+0

Non, n'utilisez pas ToLocalTime() ou ToUniversalTime(). Ils appliquent la correction du fuseau horaire en utilisant le fuseau horaire de la machine sur laquelle ils s'exécutent. C'est le problème que vous avez essayé de résoudre, pas répété. Si vous convertissez toujours en UTC, c'est absolu et il ne sera jamais ajusté pour l'heure d'été. Si vous utilisez .NET 3.5 ou version ultérieure, utilisez TimeZoneInfo.ConvertTimeFromUtc() et ConvertTimeToUtc() avec un objet TimeZoneInfo être explicite au sujet de votre conversion. Je les ai utilisés et ils fonctionnent comme prévu. – Suncat2000

Répondre

2

Vous pouvez essayer de changer le DateTimeKind sur la valeur du côté client. Non spécifié De cette façon, WCF et Entity Framework n'auront pas assez d'informations pour essayer d'être astucieux à propos de la conversion.

DateTime.SpecifyKind
DateTimeKind


Faisant suite à ce ne fonctionne pas et votre commentaire dans la question ...

Tout d'abord, qu'est-ce que vous essayez de faire - ne voulez-vous que les valeurs stockées dans la base de données doit être dans le fuseau horaire du client - dans votre cas au Royaume-Uni - ou voulez-vous qu'il soit stocké en UTC? D'après mon expérience, la meilleure solution est de l'enregistrer comme UTC sinon vous allez vraiment confondre les choses si vous avez plusieurs clients dans des fuseaux horaires différents.

En supposant que vous voulez le stocker comme UTC, vous devez le convertir en UTC côté client avant de le passer sur le réseau (DateTime.ToUniversalTime), vous devez ensuite vous assurer que le serveur le reconnaît comme UTC (il doit faites-le automatiquement, mais vous voudrez peut-être appeler SpecifyKind après l'avoir reçu juste pour être sûr). Entity Framework devrait puis le stocker dans la base de données non modifiée - que vous décrivez dans votre commentaire.

Maintenant, le truc est de se rendre compte que le temps vous obtenez au client lorsque vous récupérez les données seront en UTC. Ainsi, lorsque l'heure du Royaume-Uni ne correspond plus à l'heure UTC, cela semble faux. Donc, assurez-vous d'appeler DateTime.ToLocalTime sur toutes les valeurs que vous obtenez du serveur avant de les afficher à l'utilisateur.

Au moins c'est l'approche I prendrait.

(Oh, et en tant que développeur britannique, je trouve vraiment utile de régler l'heure sur mon ordinateur client à n'importe quel moment du Royaume-Uni en faisant ce genre de travail - sinon vous allez introduire des bugs que vous ne choisirez pas sur jusqu'à ce que nous passons sur la BST Dans mon expérience, cela a tendance à se produire une fois que vous êtes allé en direct)

+0

Cheers - Je vais vous donner que vont maintenant ... – TobyEvans

+0

Nope - qui n'a pas fait une différence, en utilisant l'un des paramètres. J'ai mis le DateTimeKind à Unspecified, UTC et Local - il l'a toujours enregistré comme l'heure locale. Pour vous assurer que j'utilisais le code que je pensais que j'étais (et non une version en cache), j'Enveloppez la conversion de date dans une méthode d'assistance qui a également créé une nouvelle date de l'ancien, et changé si je voulais millisecondes ou non : Merci, mais pas la réponse, malheureusement ... – TobyEvans

+0

Salut - Eh oui qui l'explique bien. Je vais devoir penser à juste des dates (pour représenter des jours entiers/mois/années) cependant - ils doivent rester les mêmes, et je ne veux pas qu'ils rétrogradent une heure au jour/mois précédent pendant la BST. à votre santé – TobyEvans

Questions connexes