이시안 개발 블로그

Vue 개발도구 Memory Leak 해결하기 본문

📖삽질

Vue 개발도구 Memory Leak 해결하기

ICAN 2022. 10. 15. 00:24

Vue 개발도구 Memory Leak 해결하기?


Vue 프로젝트 작업 중 Vue devtools를 켠 순간

띠용

Possible EventEmitter memory leak detected.

EventEmitter에서 메모리 누수가 날 수도 있다는 경고 메시지와 함께 브라우저가 작동하지 않게 되었습니다.

개발 생산성을 높여주는 Vue 개발 도구를 부활시키기 위해 삽질한 내용을 기록해보려고 합니다.

⚽ 일단 시키는대로

경고 메시지에서는 EventListener의 수를 늘리라고 합니다.

프로젝트에서는 web3 모듈을 사용하고 있었으며 web3의 provider가 EventListener를 관리하고 있습니다.

listener의 수를 최대 1000으로 설정

기본 설정이 100(Node.js는 10)이어서 과감하게 1000으로 늘려봤습니다.

1000개로도 안된다?

1000개로 늘렸지만 경고 메시지는 계속 떴고, 브라우저는 계속 멈췄습니다.

근데 해당 이슈 발생 전에는 항상 Pinia가 web3 store를 불러온 것을 확인할 수 있었습니다.

왜 발생했을까?

프로젝트에서는 몇몇의 전역 상태를 관리하도록 Pinia를 쓰고 있었습니다.

store에서 전역 상태들을 관리하고 있었고, store를 사용하는 데는 이상이 없었으니 Pinia의 store는 분명 제대로 역할을 하고 있다고 생각했습니다.

 

web3 store는 언제 저 메시지를 띄운 것일까 생각해봤습니다.

  1. 프로젝트가 구동 중일 때 store 또한 함께 생성됨
  2. Vue 개발 도구를 클릭
  3. Vue 개발 도구가 컴포넌트, Pinia, Routes 등등 데이터를 동적으로 불러옴
  4. web3 store를 불러온 후 메모리 누수 발생!

Vue 개발도구를 사용하면 Component, Event, Pinia, Route 등 프로젝트의 정보를 보여주는 데 web3 store의 정보를 불러오고 개발자 도구에 보여줄 때 문제가 발생한 것을 알았습니다.

 

문제 해결

 

Pinia 🍍

Intuitive, type safe, light and flexible Store for Vue

pinia.vuejs.org

공식 문서에는 외부 라이브러리에서 생성한 인스턴스를 스토어에 저장할 때 markRaw()를 사용하라고 합니다.

function markRaw(value) {
  def(value, "__v_skip" /* ReactiveFlags.SKIP */, true);
  return value;
}

markRaw() 함수는 스토어에 저장할 인스턴스를 def() 함수에 __v_skip과 true 값을 함께 넘깁니다.

__v_skip은 Proxy 객체를 생성하지 않고 데이터를 직접 반환하게 하는 플래그 값입니다.

반응성을 해제하고 원본 객체를 넘김으로써 복잡한 써드파티 라이브러리의 객체를 스토어로 관리할 수 있게 됩니다.

const def = (obj, key, value) => {
  Object.defineProperty(obj, key, {
      configurable: true,
      enumerable: false,
      value
  });
};

def() 함수는 Object.defineProperty() 함수를 호출합니다. 객체의 속성을 변경하거나 추가한 후 새로운 객체를 넘겨주는 역할을 하는데 configurable과 enumerable 속성을 설정하는 것을 확인할 수 있었습니다.

 

저의 경우엔 web3.js 라이브러리를 사용하고 있었고, web3Api에 몇몇 정보를 스토어로 관리하기 위해 Pinia를 사용했었습니다.

 

Pinia의 actions 속성에서 markRaw() 함수를 이용해 상태를 저장하게끔 하니 해결할 수 있었습니다.

성공

메모리 누수 관련 로그가 찍히지 않고, Vue 개발 도구도 사용할 수 있게 되었습니다. 🤪🤪🤪

 

참고자료
Vue 공식문서
MDN
Pinia 공식문서
https://dev.to/jinjiang/understanding-reactivity-in-vue-3-0-1jni
Comments