非同步系結和儲存體的運作方式

非同步儲存體可增強 COM 結構化儲存規格,以支援在高延遲、低速連結網路上下載儲存體物件,例如網際網路。 非同步儲存體可與非同步 Moniker 搭配運作,以提供完整的非同步系結行為。

內嵌在網頁中的檔物件

當使用者按一下代表網頁內嵌檔的連結時,會發生下列事件:

  1. 瀏覽器會呼叫 MkParseDisplayName 函式,並傳遞連結 URL。

  2. MkParseDisplayName 會剖析 URL、建立對應的非同步 Moniker,並傳回 Moniker IMoniker 介面的指標。

  3. 瀏覽器會呼叫 IsAsyncMoniker 來判斷 Moniker 是否為非同步、建立系結內容、向系結內容註冊 IBindStatusCallback 介面、只有在 Moniker 是非同步,並呼叫 IMoniker::BindToObject,傳遞系結內容。

  4. Moniker 會系結至 物件,並查詢 IPersistMoniker 介面,指出物件是否支援非同步系結和儲存體。 如果物件傳回 IPersistMoniker的指標:

    1. URL Moniker 會呼叫 IPersistMoniker::Load,並將自己的 IMoniker 指標傳遞至物件。
    2. 物件會修改系結內容,選擇它是否想要封鎖或非封鎖儲存體、註冊自己的IBindStatusCallback,並在透過IPersistMoniker::Load收到的指標上呼叫IMoniker::BindToStorage
    3. Moniker 會建立異步儲存體、保留包裝函式物件的 IFillLockBytes 介面參考、在根儲存體上註冊 IProgressNotify 介面,以及呼叫 IPersistStorage::Load,傳遞非同步儲存體的 IStorage 指標。 當資料在背景執行緒上 () Moniker 呼叫 IFillLockBytes 以填滿暫存檔上的 ILockBytes
    4. 物件會從儲存體讀取資料,並在收到足夠的資料以考慮本身初始化時從 IPersistMoniker::Load 傳回。 如果物件嘗試讀取尚未下載的資料,下載者會收到 IProgressNotify上的通知。 在 IProgressNotify::OnProgress方法內,下載執行緒會在強制回應訊息迴圈中封鎖,或讓非同步儲存體傳回E_PENDING,視物件是否要求封鎖或非封鎖儲存體而定。
  5. 如果物件未實作 IPersistMoniker,Moniker 會查詢 IPersistStorage,這表示物件的永續性狀態儲存在儲存體物件中。 如果物件傳回 IPersistStorage的指標:

    1. Moniker 本身會呼叫 IMoniker::BindToStorage ,要求封鎖 IStorage (,因為物件不是非同步感知) 、建立異步儲存體、保留包裝函式物件的 IFillLockBytes 介面參考、在根儲存體上註冊 IProgressNotify 介面,以及呼叫 IPersistStorage::Load,並傳遞非同步儲存體的 IStorage 指標。 當資料在背景執行緒上 (,) Moniker 呼叫 IFillLockBytes 以填滿暫存檔上的 ILockBytes
    2. 物件會從儲存體讀取資料,並在收到足夠的資料以考慮本身初始化時從 IPersistStorage::Load 傳回。 如果物件嘗試讀取尚未下載的資料,則會在 IProgressNotify上收到通知。 在 IProgressNotify::OnProgress 方法內,下載執行緒一律會封鎖在強制回應訊息迴圈中。
  6. 無論下載是同步還是非同步,Moniker 都會從 IMoniker::BindToObject傳回,而瀏覽器會收到它所要求的初始化物件。

  7. 瀏覽器會查詢 IOleObject ,並將物件裝載為 Document 物件。 (此時,物件可能無法完全初始化,但足以顯示有用的內容,在此情況下,下載會繼續在 background.)