2012-09-01 12 views
5

मेरी आवश्यकता यहां काफी मानक है; मुझे उपयोगकर्ताओं को अपने वर्तमान टाइमज़ोन का चयन करने और अपने खाते के विरुद्ध सहेजने की अनुमति देने की आवश्यकता है। इसके बाद मैं संग्रहीत DateTime मानों को स्थानीयकृत समय में कनवर्ट करने के लिए इस मान का उपयोग करूंगा।उपयोगकर्ताओं को संग्रहीत करना समय क्षेत्र वरीयता

मेरे वर्तमान सोच है कि मैं उपयोगकर्ताओं को एक सूची में से एक नेट TimeZoneInfo.Id चयन करने के लिए अनुमति देगा (DB में आयोजित अधिक अनुकूल वर्णन अनुमति देने के लिए लेकिन TimeZoneInfo.GetSystemTimeZones() का उपयोग कर साथ बनाया) है - मैं फिर प्रासंगिक TimeZoneInfo उदाहरण वापस जाने के लिए यह मान का उपयोग करेगा TimeZoneInfo.FindSystemTimeZoneById() का उपयोग करके और रूपांतरण करें। मुख्य समस्या यह है कि मैं यहां देखता हूं कि TimeZoneInfo.Id रजिस्ट्री में एक मान है और यह "मानक" आईडी नहीं है (उदाहरण के लिए ओल्सन की तुलना में)। इस प्रकार, यह संभव है कि सर्वर अपडेट/माइग्रेशन संग्रहीत आईडी को पूरी तरह से अमान्य कर सकता है और रूपांतरण को तोड़ सकता है ..

संक्षेप में - क्या यह दृष्टिकोण मान्य/सुरक्षित है? यदि नहीं, तो क्या अतिरिक्त तर्क के बिना डेलाइट बचत आदि को संभालने के दौरान उपयोगकर्ताओं को टाइमज़ोन वरीयता संग्रहित करने का एक बेहतर तरीका है?

+0

क्या आपने ['DateTimeOffset'] (http://msdn.microsoft.com/en-us/library/system.datetimeoffset.aspx) देखा है? या ['नोडाटाइम'] (http://code.google.com/p/noda-time/)? – Oded

+0

संबंधित: http://stackoverflow.com/q/2532729/1583 – Oded

+1

@ ओडेड डेटटाइम ऑफसेट के साथ समस्या यह है कि यह डे लाइट सेविंग्स जागरूक नहीं है – Paparazzi

उत्तर

8

मुझे अभी यह पुराना-आश अनुत्तरित प्रश्न मिला है, इसलिए सोचा कि मुझे इसमें एक स्टैब लेना चाहिए।

संक्षेप में - क्या यह दृष्टिकोण वैध/सुरक्षित है?

यह सब इस बात पर निर्भर करता है कि आप उनके साथ क्या करने की योजना बना रहे हैं।

यदि आप इसे सर्वर-साइड कोड में उपयोग कर रहे हैं, तो हाँ। आप बस टाइमज़ोन के Id स्टोर करते हैं, और उपयोगकर्ता को DisplayName संबंधित दिखाते हैं। FindSystemTimeZoneById और GetSystemTimeZones इसके लिए पूरी तरह से मान्य हैं।

ध्यान रखें कि Id मान हमेशा समान होते हैं - DisplayName गुण Windows ऑपरेटिंग सिस्टम की भाषा के आधार पर भिन्न होंगे जो आप कोड चला रहे हैं। कार्यान्वयन संस्कृति जागरूक नहीं है, इसलिए नेट में एक अलग लक्षित संस्कृति सेट करना DisplayName स्ट्रिंग को नहीं बदलेगा।

माइक्रोसॉफ्ट विंडोज समय क्षेत्र डेटाबेस में रिकॉर्ड उचित रूप से स्थिर हैं, और विंडोज अपडेट के माध्यम से अद्यतन रखा जाता है। जानकारी के कुछ रजिस्ट्री से आता है, लेकिन स्थानीय संसाधन स्ट्रिंग tzres.dll से आती हैं। बेशक, यह सब आपसे TimeZoneInfo और संबंधित कक्षाओं से छिपा हुआ है।

हालांकि, यदि आप इन समय क्षेत्र Id अन्य सिस्टमों के मानों को पार कर रहे हैं - देखें। विंडोज के पूर्व संस्करणों के साथ कुछ बदलाव हैं। उदाहरण के लिए, मुझे पता है कि डिस्प्ले नाम उन सभी में "जीएमटी" कहते हैं, और अब "यूटीसी" और अधिक सही ढंग से कहते हैं। Id मान समान हैं, लेकिन कौन जानता है कि वास्तव में और क्या नहीं है। विशेष रूप से यदि लक्षित कंप्यूटर को आपके पास Windows अपडेट का एक ही सेट प्राप्त नहीं हुआ है। वैसे - अपडेट की घोषणा here है।

आप Windows समय क्षेत्र डेटाबेस के बारे में कुछ बातें पता होना चाहिए:

  • यह प्रति कैलेंडर वर्ष में दो से अधिक डीएसटी संक्रमण का प्रतिनिधित्व करने में असमर्थ है। उदाहरण के लिए - in 2010, Cairo, Egypt had four transitions। माइक्रोसॉफ्ट ने a hotfix जारी किया, लेकिन यह केवल एक समझौता सुधार किया, ऐतिहासिक रूप से सटीक नहीं। ऐसे अन्य क्षेत्र हैं जिनके पास ऐतिहासिक परिवर्तन हैं जिन्हें ठीक से प्रदर्शित नहीं किया जा सकता है।

  • विंडोज़ XP/2003 और Vista/2008 के बीच कुछ चीजें बदलीं। इस here के बारे में कुछ वास्तव में अच्छी जानकारी है, साथ ही रजिस्ट्री का उपयोग कैसे किया जाता है इसके बारे में बहुत सारी जानकारी है।

  • माइक्रोसॉफ्ट केवल अपने स्वयं के समय क्षेत्र डेटाबेस के साथ प्रमुख खिलाड़ी है। शेष दुनिया IANA/Olson database का उपयोग करती है। इससे अंतःक्रियाशीलता की समस्याएं होती हैं। मेरे पास the timezone tag wiki में इसका एक सभ्य लेखन है।

तुम भी पता होना चाहिए कि TimeZoneInfo अलंघनीय DateTime और DateTimeOffset वर्गों से जुड़ा हुआ है। इनके पास क्विर्क का अपना सेट है। DateTimeOffset कुछ हद तक उपयोग योग्य है, लेकिन DateTime बारीकियों के साथ झुका हुआ है। पढ़ें:

NodaTime उपयोग करने के लिए एक दूर बेहतर नेट में दिनांक और समय का हल है द्वारा। यह लाइब्रेरी दोनों समय क्षेत्र डेटाबेस, उनके बीच सीएलडीआर मैपिंग सहित लागू करती है। यह एक बहुत सुरक्षित एपीआई भी प्रदान करता है जो आपको परेशानी में नहीं आने देता है। इसमें थोड़ा सा सीखना पड़ सकता है, लेकिन इससे पहले कि आप इसे जानते हों, आप LocalDateTime, ZonedDateTime, OffsetDateTime और Instant जैसी कक्षाओं का उपयोग करेंगे।

आपको अभी भी समस्या है कि समय क्षेत्र डेटाबेस अक्सर अपडेट किया जाता है, क्योंकि हम राजनेताओं के लिए समय-समय पर नियम छोड़ते हैं। लेकिन the TZDB folks डेटाबेस को ऐतिहासिक रूप से सटीक रखने और ज़ोन नाम बदलने पर उपनाम/लिंक प्रदान करने का एक बहुत अच्छा काम करते हैं। आप tz नाम here की एक सूची देख सकते हैं।

इसके अलावा, यदि आप नोडाटाइम के साथ जाते हैं, तो आप या तो वितरण में संकलित TZDB की प्रतिलिपि के साथ चिपकने का विकल्प चुन सकते हैं, या आप अपनी प्रतिलिपि अपने आवेदन के साथ भेज सकते हैं। आप (सैद्धांतिक रूप से) IANA से नवीनतम संस्करण को खींचने के लिए अपना कोड लिख सकते हैं और अपना एप्लिकेशन अपडेट कर सकते हैं - सभी मेजबान ऑपरेटिंग सिस्टम पर भरोसा किए बिना।

+0

पूरे timezoneinfo.ID चीज को समझ में नहीं आता है। आईडी एक पहचानकर्ता होने की उम्मीद है जो कुछ आईएसओ मानक तरीके का पालन करता है। हालांकि, मुझे अभी पता चला है कि 'FindSystemTimeZoneById' विंडोज के विभिन्न संस्करणों में सही ढंग से काम नहीं करता है।एक संस्करण में, लौटाई गई स्ट्रिंग सभी कम मामला है और दूसरा यह ऊंट का मामला है और मामलों को और भी खराब बनाने के लिए, FindSystemTimeZoneById केस असंवेदनशील नहीं है। जाओ पता लगाओ! – Rajiv

+0

@ राजीव - समय क्षेत्र के लिए कोई आईएसओ मानक नहीं हैं। आईएएनए/ओल्सन पहचानकर्ता (ऊपर वर्णित) एक मानक के पास सबसे नज़दीकी चीज हैं। विंडोज़ आईडी के संबंध में, मैंने कभी भी किसी भी तरह का सामना नहीं किया है, जब तक कि वे किसी और चीज से उलझ गए न हों। जैसा ऊपर बताया गया है, आईडी तब तक सुसंगत होनी चाहिए जब तक कि आप एक नए-पेश किए गए समय क्षेत्र के बारे में बात नहीं कर रहे हैं जिसे एक सिस्टम पर स्थापित किया गया है लेकिन दूसरा नहीं। उदाहरण, [KB3093504] (https://support.microsoft.com/en-us/kb/3093503) ने हॉटफिक्स में "उत्तरी कोरिया मानक समय" पेश किया। –