手寫vue3的響應式核心reactive

近期在看Vue3的源碼,看完后也根據(jù)一些閱讀文檔的時候的注釋,打算手寫實現(xiàn)模擬vue3的核心代碼,作為讀書筆記,方便后續(xù)面試的時候進行復習

你需要掌握的知識點

  • Proxy & Reflect
  • WeakMap
reactive 的實現(xiàn)
typescript

import { isObject } from '@vue/shared'
import { mutableHandlers, ReactiveFlags } from './basicHandler'

// 收集全局的響應式對象,key為傳入的target,value為其代理對象
const reactiveMap = new WeakMap()

export function reactive(target) {
  // reactive只能接收對象類型
  if (!isObject(target)) return

  // 避免傳入一個已經(jīng)代理過的對象
  // 未代理之前,target.__v_isReactive 為 undefined,代理過,則為true。
  // 詳情看 mutableHandlers
  if (target[ReactiveFlags.IS_REACTIVE]) {
    return target
  }

  // 避免對同一個對象進行多次代理
  const reactiveValue = reactiveMap.get(target)
  if (reactiveValue) {
    return reactiveValue
  }

  const proxy = new Proxy(target, mutableHandlers)
  reactiveMap.set(target, proxy)
  return proxy
}

mutableHandlers 的實現(xiàn)
import { track, trigger } from './effect'
import { isObject } from '@vue/shared'
import { reactive } from './reactive'
export enum ReactiveFlags {
  IS_REACTIVE = '__v_isReactive'
}

export const mutableHandlers = {
  get(target, key, receiver) {
    if (key === ReactiveFlags.IS_REACTIVE) {
      return true
    }
    // 收集依賴
    // Fernando: 現(xiàn)在不需要知道他是怎么實現(xiàn)的,你只需要知道他在這里的操作就是收集依賴。后續(xù)章節(jié)我會補上
    track(target, 'get', key)
    const result = Reflect.get(target, key, receiver)
    if (isObject(result)) {
      // 實現(xiàn)深度代理,相較于vue2在初期階段就遞歸進行數(shù)據(jù)劫持,性能更好,取值的時候再進行代理
      return reactive(result)
    }
    return result
  },
  set(target, key, value, receiver) {
    const oldValue = target[key]
    const result = Reflect.set(target, key, value, receiver)

    if (oldValue !== value) {
      // 觸發(fā)更新依賴相關的effect
      // Fernando: 現(xiàn)在你不需要知道他是怎么實現(xiàn)的,你只需要知道他在這里會去觸發(fā)更新即可
      trigger(target, 'set', key, value, oldValue)
    }
    return result
  }
}

以上則為 vue3 對象代理的部分骨架代碼,后續(xù)我會持續(xù)更新,github搶先看
https://github.com/Fernando-lu/fernando-vue

最后編輯于
?著作權歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務。
禁止轉(zhuǎn)載,如需轉(zhuǎn)載請通過簡信或評論聯(lián)系作者。

相關閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容