npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

await-selector

v1.0.1

Published

Detect Inserted DOM Elements Matching a Selector

Downloads

203

Readme

awaitSelector()

Do away with polling; let the DOM tell you when dynamically added elements are available. If you have ever had to deal with the dirty job of writing ugly code to wait for an element to appear in the DOM, you know how much it can hurt your soul.

The two typical solutions from days of yore are either to keep polling the DOM to see if the required elements have been dynamically inserted yet or, even worse, just set a really long delay on a setTimeout() call and hope it's long enough that the content is available at the end of it.

Now you can use await-selector to take care of it in a much cleaner way.

See also my Medium article: Promise-Based Detection of Element Injection »

Install

npm install await-selector

awaitSelector() Example

awaitSelector() will resolve the first time a selector appears in the DOM (or if it is already in the DOM when called).

import awaitSelector, { watchAwaitSelector } from 'await-selector'

// Promises

// a given element will only ever be detected a maximum of once
awaitSelector('.news-story', '#news-feed')
  .then(elements => { // elements is an array of native DOM elements
    // ... do something with the new element(s) ...
  })

// Async/Await

(async () => {
  const elements = await awaitSelector('.comment', '#comment-list')
  // ... do something with the new element(s) ...
})()

watchAwaitSelector() Example

watchAwaitSelector() will fire a callback every time a selector appears in the DOM.

watchAwaitSelector(
  elements => {
    // ... do something with the new element(s) ...
  },
  '.post-body',
  '#posts'
)

Usage

Function Parameters

  • selector - the CSS selector used to select new matching elements
  • (rootNode) - the element or selector that should be used as the subtree root to watch for DOM changes; default: document
  • (fallbackDelay) - the delay (in millisecs) to wait between lookups if using the fallback polling method (if MutationObserver is not available); default: 250

awaitSelector Return Value

  • Promise resolving an array containing elements not yet found matching your selector found in the DOM within the rootNode

watchAwaitSelector

  • Your callback to watchAwaitSelector can return false to stop watching

Demo

Below is a snippet of an example, which you can see in an interactive example on this CodePen. It simply logs elements with the matching class name whenever they are inserted into the DOM.

const dumpElements = elements =>
  elements.forEach(el => console.log('Successfully detected element:', el.outerHTML))

const createAwaiter = () => {
  const subtreeRoot = document.querySelector('#the-parent')
  
  awaitSelector('.my-list-item', subtreeRoot)
    .then(dumpElements)
    .then(createAwaiter)
    .catch(error => console.log('Hmm. Something borke!', error.message))
}

createAwaiter()

You can use watchAwaitSelector instead of the code in the createAwaiter() code in the snippet above, which simply invokes itself:

const subtreeRoot = document.querySelector('#the-parent')
watchAwaitSelector(dumpElements, '.my-list-item', subtreeRoot)

As a fallback, if you're concerned about older browsers, the function will automatically use the aforementioned polling to look for new elements that match your selector(s). You can specify the polling delay, but it defaults to 250ms.