Blog>
Snippets

WeakMaps for Managing References

Show a practical use of WeakMaps in JavaScript to hold references to DOM elements or objects without preventing their garbage collection, thus avoiding potential memory leaks.
// Function to add a DOM element and attach additional data using a WeakMap
function attachElementData(el, data) {
  // Only create the map if it doesn't exist already
  if (!window.domElementDataMap) {
    window.domElementDataMap = new WeakMap();
  }
  // Associate data with the DOM element in a WeakMap
  window.domElementDataMap.set(el, data);
}

// Example usage:
// const element = document.createElement('div');
// attachElementData(element, { property: 'value' });
The function `attachElementData` attaches arbitrary data to a DOM element using a WeakMap, which will not prevent the DOM element from being garbage collected when it's no longer in use.
// Function to retrieve data associated with a DOM element
function getElementData(el) {
  if (window.domElementDataMap) {
    return window.domElementDataMap.get(el);
  }
  return undefined;
}

// Example usage:
// const data = getElementData(element);
// if (data) console.log('Element data:', data);
The function `getElementData` retrieves data associated with a DOM element that was previously stored using the WeakMap `domElementDataMap`.
// Event listener that cleans up after itself using a WeakMap
let clickListenersMap = new WeakMap();

function addSelfCleaningListener(element, callback) {
  // Wrapper function that helps in removing event listener
  const listener = (event) => {
    callback(event);
    element.removeEventListener('click', listener);
    clickListenersMap.delete(element);
  };
  // Add the listener to the element and keep a reference in the WeakMap
  clickListenersMap.set(element, listener);
  element.addEventListener('click', listener);
}

// Example usage:
// addSelfCleaningListener(document.getElementById('myButton'), () => {
//   console.log('Button clicked and listener removed!');
// });
This example creates an event listener that automatically cleans up after itself to prevent memory leaks. The listener reference is stored in a WeakMap, so it doesn't prevent garbage collection once the element goes away.