dubbo debug過程當中發現的IDEA有趣的小發現及dubbo消費者debug小tips

原本是在debug dubbo的reference bean的init()過程,由於ReferenceBean是繼承了Spring FactoryBean接口的,spring

因此初始化入口天然就是FactoryBean定義的函數,getObject()。在該方法內,只顯示調用了ReferenceConfig.get()。bash

內容以下:異步

public synchronized 
複製代碼

能夠看到,核心的初始化代碼就在init()中。這裏,會首先判斷factoryBean 要建立的bean實例ref是否已經初始化,若未初始化,纔會進行Init()調用。編輯器

因此,我斷點天然就打在ReferenceBean.getObject()上。函數

啓動spring。測試

反覆屢次,我發現,只要我在ReferenceBean.getObject()或者ReferenceConfig.get()上加上斷點,ref實例就會莫名其妙地已經被初始化過,proxy$xxxx。spa

這就奇怪了。debug

這個ReferenceBean的整個的入口函數,getObject()的觸發,是在個人控制下的啊,即:調試

springContext.getBean("referenceBeanId");code

那我就在想,是否是spring container的初始化有異步的部分呢?因此我就直接把斷點加載init()方法上。

而後我返回調試後發現,若是我只將斷點加在Init(),而ReferenceBean.getObject()與ReferenceConfig.get()不加斷點的話,init()方法裏是正常進入,且進入的代碼initialized也是false的

private void 
複製代碼
}
複製代碼
就是init()開頭4行代碼處。
後來我就想,是否是哪裏給反射注入了呢?固然,我也沒啥發現,我就直接百度了。結果果不其然。
在網上發現了一篇一樣問的文章。那我的在源碼里加了一段註釋,以下

圖片已損壞

圖片已損壞

能夠看到,AbstractConfig.toString()方法居然反射調用了ReferenceConfig.init()方法。。。

AbstractConfig.toString()的代碼以下:

image

能夠看到,這個if裏是對全部getter經過的,經過後,又再接下來的紅框處調用了我擦,也就是說,ReferenceBean.getObject()給調用了,進而也就init()給調用了。

後來,原文做者又作了這樣一個測試,得出了最終結果

圖片已損壞

結果就是:

IDEA這類編輯器的debug功能爲了在斷點處可以顯示類實例的相關信息,就會反射調用相關類實例的toString()方法!!!!

思考:

DUBBO爲何要在AbstractConfig.toString()的反射調用init()呢?真尼瑪奇怪。。。。

答案:

dubbo的AbstractConfig的toString方法反射調用只是爲了輸出時可以更全面一點。可是由於AbstractConfig的子類

ReferenceBean實現了FactoryBean接口,這個接口是Spring用來獲取Bean實例的工廠bean,生成bean的方法就叫getObject,正好符合了toString裏面邏輯,而getObject裏是要初始化bean的。因此,就這麼巧地對應上了

相關文章
相關標籤/搜索