背景描述
因為業務需求的需要,我們需要在原來項目中的一個DTO類中新增兩個字段(我們項目使用的是dubbo架構,這個DTO在A項目/服務的domain包中,會被其他的項目如B、C、D引用到)。但是這個DTO對象已經在Redis緩存中存在了,如果我們直接向類中增加字段而不做任何處理的話,那么查詢操作查出來的緩存對象就會報反序列化失敗的錯誤,從而影響正常的業務流程,那么來看一下我的解決方案吧。
升級緩存版本號
我們的正式環境和預發布環境是共用Redis和Mysql。如果修改了DTO且沒有加@JsonIgnoreProperties(ignoreUnknown = true)這個注解。
那么DTO所在的A項目發到預發布之后,會啟動一個后台定時任務把最新的DTO對象刷新到緩存中去,但是除了這個工程以外的其他依賴服務如果沒有發的話,那么他們jar包里面的domain還是舊的DTO。
那么這個時候取出來的緩存(最新的DTO的緩存)就會有反序列化的錯誤,發包的延遲和預發布驗證的時間都會導致線上反序列化失敗,從而阻塞業務。
解決方案就是升級緩存的版本號(修改原來緩存DTO的Redis的Key值)
緩存key升級版本號,在其他未更新的應用中的緩存key已經在跑的jar包里面,他們的key是舊的,比如v1,那么v1對應的DTO就是舊的DTO。
升級后新的DTO版本為v2那么發起來的自身服務刷新最新的DTO緩存是放到v2的key里面的,即v2->新的DTO,v1->舊的DTO。這樣可以保證不會有反序列化的問題。
注意
改版本號一定要在第一次發的時候改上去才好,不然你按v1發的版,發現問題再改成v2已經就晚了,因為已經把新的DTO刷到v1里面了,線上的依賴服務里面的domain包就是v1撈出來肯定異常。
如果發生這種情況只能再發v2版本到預發布,同時刪掉線上v1的緩存。
如果對您有幫助,請不要忘了給翎野君點贊。