一区二区久久-一区二区三区www-一区二区三区久久-一区二区三区久久精品-麻豆国产一区二区在线观看-麻豆国产视频

如何解決分布式系統(tǒng)中的跨時區(qū)問題[原理篇]

  一、場景以及需求

   為了讓大家本文介紹的主題有一個比較直觀的認識,我們給出一個具體的應用場景。一個跨國公司開發(fā)一套統(tǒng)一的辦公系統(tǒng),供遍布全球的所有分公司使用。客戶端的UI采用Smart Client (Windows Forms應用),而主要的業(yè)務邏輯均通過WCF服務的形式提供。我們將承載業(yè)務服務的服務器成為應用服務器,如右圖(點擊看大圖)所示,應用服務器部屬于中國境內(nèi)(東8區(qū))。主要的客戶端(分公司)分布于三個主要的國家和地區(qū):北美、歐州和澳洲。

  不論客戶端和服務器之間,還是不同的客戶端之間所處的時區(qū)均不相同,在進行時間處理的時候就會遇到一些麻煩:某個客戶端通過服務調(diào)用獲取的時間值應該基于哪個時區(qū)?對于這個問題,不同的場景可能有不同的要求。在大部分情況下,我們希望獲取的時間值就是基于客戶端的本地時區(qū)。不過也有些場景我們希望獲取的時間值對應的時區(qū)是描述對象基于的那個時區(qū)。比如說,美國分公司于當?shù)貢r間9月1號早8點舉行開業(yè)典禮,歐洲分公司員工讀取這條信息就沒有必要將時間轉(zhuǎn)換成基于本地時區(qū)的時間。

  不過,本文不考慮這種情況,我們的最終要求是:客戶端應用根本不用考慮時區(qū)問題,就像是一個單純的本地應用一樣。客戶端調(diào)用服務傳入的時間是DateTimeKind.Local時間或者DateTimeKind.Unspecified時間,同理通過服務調(diào)用返回的時間也應該是基于客戶端所在時區(qū)的時間。

  二、解決方案實現(xiàn)原理

  現(xiàn)在我們就來談談如何解決上面提出的問題。既然時區(qū)的處理不能在客戶端做,換言之就必須在服務端實現(xiàn)。我們的一個前提是:在數(shù)據(jù)庫中不存儲時區(qū)的任何信息。在這樣一個前提下實現(xiàn)上述的目標,需要解決兩個問題:時間的保存和時間獲取。

  在時間的保存方面,既然數(shù)據(jù)庫中能保存任何時區(qū)偏移之類的信息。在這種情況下,我們必須讓所有保存在數(shù)據(jù)庫中的時間都是基于同一個時區(qū)。我們可以選擇應用服務器所在的時區(qū),也可以直接采用UTC時間。我們的方案采用后者,即數(shù)據(jù)庫所有時間保存為UTC時間 。

  時間在數(shù)據(jù)庫中的存儲形式確定了,現(xiàn)在又出現(xiàn)一個問題:客戶端傳來的時間為客戶端所在時區(qū)的當?shù)貢r間,服務端接收到客戶端發(fā)送的時間后,需要基于客戶端相應時區(qū)轉(zhuǎn)換成UTC時間才能保存到數(shù)據(jù)庫。那么,服務端如何獲取客戶端所在的時區(qū)信息呢?將其作為服務操作的參數(shù)肯定是不可取的。

  如果你看過我之前的WCF系列文章,可能會記得我有一篇介紹如何通過WCF擴展實現(xiàn)在客戶端和服務端之間傳遞上下文的文章:《通過WCF Extension實現(xiàn)Context信息的傳遞》。在這篇文章中我通過WCF擴展實現(xiàn)了將可戶端的Culture和UICulture自動傳向了服務端,從而確保兩邊保存一樣的語言文化環(huán)境上下文。如果我們能夠?qū)⒒诳蛻舳吮镜氐?a >TimeZoneInfo作為上下文進行傳遞,就能解決服務端對客戶端的時區(qū)識別問題了。

  關(guān)于保存時間的處理大體可以通過上面的序列圖(點擊看大圖)來描述。客戶端將基于本地時區(qū)的DateTimeKind.Local或者DateTimeKind.Unspecified時間作為輸入操作調(diào)用某個服務,與此同時,本地的TimeZoneInfo序列化后作為上下文傳遞到服務端。服務端接將接收到的時間,根據(jù)接收到TimeZoneInfo上下文轉(zhuǎn)換成DateTimeKind.Utc時間,并保存到數(shù)據(jù)庫中。

`當客戶端調(diào)用服務獲取某個時間的時候,本地的同樣作為上下文信息被傳遞到服務端。借助于這個TimeZoneInfo,服務端可以將數(shù)據(jù)庫中以UTC形式保存的時間轉(zhuǎn)換成基于客戶端時區(qū)的DateTimeKind.Local時間。下圖(點擊看大圖)所示的序列圖反映了這個過程。

  三、TimeZoneInfo的序列化問題

  在《談談你最熟悉的System.DateTime[上篇]》對TimeZoneInfo這個類進行介紹中,我說該類是可以被序列化的,序列化對于解決跨時區(qū)問題很重要。就是因為我們需要將TimeZoneInfo作為上下文在客戶端和服務端進行傳遞,換言之,就是將TimeZoneInfo對象進行序列化,將序列化后的內(nèi)容放入出棧消息(Outgoing Message)的消息報頭(Message Header)中。

  不過關(guān)于TimeZoneInfo對象序列化,我們一般并不會真正地將整個TimeZoneInfo對象交給序列化器去做序列化,而是利用定義在TimeZoneInfo中的兩個特殊的方法來進行序列化和反序列化的工作。一個是實例方法ToSerializedString,將TimeZoneInfo轉(zhuǎn)換成序列化后的一個字符串;另一個則靜態(tài)方法FromSerializedString,對序列化后的字符轉(zhuǎn)進行反序列化生成TimeZoneInfo對象。這兩個方法的定義如下:

   1: [Serializable]
   2: public sealed class TimeZoneInfo
   3: {
   4:     //Others
   5:     public static TimeZoneInfo FromSerializedString(string source);
   6:     public string ToSerializedString();
   7: } 

NET技術(shù)如何解決分布式系統(tǒng)中的跨時區(qū)問題[原理篇],轉(zhuǎn)載需保留來源!

鄭重聲明:本文版權(quán)歸原作者所有,轉(zhuǎn)載文章僅為傳播更多信息之目的,如作者信息標記有誤,請第一時間聯(lián)系我們修改或刪除,多謝。

主站蜘蛛池模板: 中国精品视频一区二区三区 | 欧美日韩一区二区三区视频 | 男人女人无遮掩免费视频 | 华人亚洲欧美精品国产 | 99超级碰碰成人香蕉网 | 色就色综合| 黑人www| 五月六月激情 | 精品一区二区三区免费观看 | 国产性精品 | 国内精品一区二区2021在线 | 国产精品日韩欧美一区二区三区 | 一二三四视频社区5在线高清视频 | 成年美女黄网站色大 | 欧美激情视频免费 | 最新eeuss影院在线观看 | 精品视频一区二区三三区四区 | 伊人色网站 | 亚洲日本一区二区三区 | 日本精品久久久久久久久免费 | 中文字幕永久免费视频 | 看全色黄大色黄大片 视 | 亚洲精品欧美 | 久久人人爽人人爽人人片宅男 | 日韩三级中文字幕 | 黄色片在线观看网站 | 日韩我不卡| 国产色视频一区二区三区 | 国产亚洲视频在线播放大全 | 加勒比一道本综合 | 国产高清区 | 97色伦图片在线观看 | 88av在线看 | 一区二区三区中文字幕 | 久久98精品久久久久久婷婷 | 91av国产精品 | 天天做天天爽爽快快 | 久久亚洲精品中文字幕三区 | 色哟哟在线观看视频高清大全 | 国产精品原创巨作av | 免费看污视频在线观看 |