1.4.1 • Published 4 years ago

requests-director v1.4.1

Weekly downloads
10
License
MIT
Repository
github
Last release
4 years ago

npm GitHub tag (latest by date) GitHub npm.io npm bundle size Snyk Vulnerabilities for GitHub Repo GitHub top language npm dev dependency version GitHub Release Date

Requests Director

Improve your web performance by downloading each file only when necessary.

requests-director is a super simple request proxy based on promises, which guarantees that each file will be downloaded: 1. Only when the desired event occurs (DOMContentLoaded, click, some Custom Event,...). 2. Using a priority that ensures that its dependencies have been loaded first.

How to use...

... as an ES6 module.

  1. Install the requests-director package and import it.
npm i @requests-director
    import rDirector from 'requests-director';
  1. Build a simple requests array. Each of them will be downloaded only when the detailed event occurs, and always maintaining the correct priority:
const requests =[
    {
        events: [
            {
                name: 'DOMContentLoaded',
                targetsQuery: 'window'
            }
        ],
        priority: 1,
        source: '/my-1st-source.js',
    },
    {
        events: [
            {
                name: 'click',
                targetsQuery: '#my-target'
            }
        ],
        priority: 2,
        source: '/my-2nd-source.js',
    },
    {
        events: [
            {
                name: '@my-custom-event',
                targetsQuery: '#my-other-target'
            }
        ],
        priority: 1,
        source: '/my-3th-source.js',
    },
    // ... others
  ];
  1. Engage the requests:
    rDirector.requests.push(requests);

And that's all. Of course, you have many more options available to customize your downloads. You can check them in the config section.

... as an external script.

  1. Get director of JSDeliver CDN service*:

    To take your CDN file, please, follow this guidelines using this link: npm.io

  1. Build a simple requests array. Each of them will be downloaded only when the detailed event occurs, and always maintaining the correct priority:
const requests =[
    {
        events: [
            {
                name: 'DOMContentLoaded',
                targetsQuery: 'window'
            }
        ],
        priority: 1,
        source: '/my-1st-source.js',
    },
    {
        events: [
            {
                name: 'click',
                targetsQuery: '#my-target'
            }
        ],
        priority: 2,
        source: '/my-2nd-source.js',
    },
    {
        events: [
            {
                name: '@my-custom-event',
                targetsQuery: '#my-other-target'
            }
        ],
        priority: 1,
        source: '/my-3th-source.js',
    },
    {
        events: [
            {
                name: '@rDirector-inDOM',
                targetsQuery: '#my-dynamic-target'
            }
        ],
        priority: 1,
        source: '/my-4th-source.js',
    },
    // ... others
  ];
  1. Safely initialize director and engage the requests:
window.rDirector = window.rDirector || { requests: [] };
window.rDirector.flavor = 'desktop';
window.rDirector.requests.push(requests);

Note that you can add multiple sources using sources property instead of source:

const requests =[
    {
        events: [
            {
                name: 'DOMContentLoaded',
                targetsQuery: 'window'
            }
        ],
        priority: 1,
        sources: [
            '/1st-source.js',
            '/2nd-source.js',
            '/3rd-source.js',
            '/4th-source.js'
        ]
    },
    // ...
  ];

And that's all. Of course, you have many more options available to customize your downloads. You can check them in the config section.

How it works.

The key concept of requests-director is the assignment of a set of events to each request, thus, each request will be queued when the first event that has been assigned occurs. Note that the request is not made automatically but is queued, in such a way that if a download with a higher priority was pending, it will be downloaded first, while those with lower priority will be downloaded later.

So the above configuration will have this behavior (if my-1st-source.js is so large that it is still loading until the end of the steps):

# On DOMContenLoaded:
- priority 1 : [my-1st-source.js]

# On #my-target click:
- priority 1 : [my-1st-source.js]
- priority 2 : [my-2nd-source.js]

# On #my-other-target @my-custom-event:
- priority 1 : [my-1st-source.js]
- priority 1 : [my-3th-source.js]
- priority 2 : [my-2nd-source.js]

# On #my-dynamic-target @rDirector-inDOM, that is, when #my-dynamic-target is added to the DOM dynamically:
- priority 1 : [my-1st-source.js]
- priority 1 : [my-3th-source.js]
- priority 1 : [my-4th-source.js]
- priority 2 : [my-2nd-source.js]

When you add a new array of request, requests-director checks each of then (if it is a valid source, and it is not loaded nor loading), and then, if it necessary, director binds the request's events that was not binded yet on every setted target.

It's that easy: for each resource you only have to establish a set of events with a set of objectives for each event (such as click on HTMLElement A and HTMLElement B, or DOMContentLoaded on document), and when the first one happens, director will queue the request in its corresponding priority.

Note that if you have this queues...

Priority 1: [a,b,c] << Current download:
Priority 2: [d,c]
Priority 3: [e,f]

... and then an event happens that adds a script or style to priority 1 (X) and another to priority 2 (Y), this would happen:

Priority 1: [a,b,c] << Current download:
Priority 1 bis: [X] << New source
Priority 2: [d,c,Y] << New source
Priority 3: [e,f]

Config.

KeyTypeRequiredDefaultDescription
eventsArray<{ name: String, targetsQuery: String }>No[ { name: 'DOMContentLoaded', targetsQuery: 'window' } ]Events that will trigger the file to be queued for download.
flavorsArray<String> OR String OR BooleanNofalseArray of flavors in which a file should be added to the queue: if a "director.flavor" has been set, also an array of flavors, and the "director.flavor" is not contained in that array, the file will not be queued.
onlyOnlineBooleanNofalseWhen it is true, that request will be added to the queue only if navigator is online.
onloadBoolean OR FunctionNofalseA callback which will be executed when the source has been loaded.
onerrorBoolean OR FunctionNofalseA callback which will be executed when the source could not have been loaded.
onsetupBoolean OR FunctionNofalseA callback which will be executed before the source download begins.
priorityNumberNo1E3The priority determines the download priority among the files currently in the queue.
sourceStringNo""The source that will be downloaded. If the source is falsy, it will simple be ignored.
sourcesArray<String>No""If you want to add multiple sources, you can use this property instead of source. The source that will be downloaded. If you want to add multiple sources, you can use this property instead of source. All sources declared (source and sources) will be downloaded. If sources is falsy, it will simple be ignored.

Built-in events.

requests-director offers some built-in events that it is usual to use them. | Event | Target | Description | |---|:-:|---| | @rDirector-inView | HTMLElement | It fires when the target is intersecting the document's viewport. | | @rDirector-inDOM | HTMLElement | It fires when the target is in the current DOM. Note that the targets search occurs everytime the DOM changes. |

DOM changes.

requests-director listens to the DOM changes to update the targets of each request. That means, you not have to worry about whether HTMLElement is in DOM when you push a requests on a 'SPA-like' application, because requests-director will (that it what happens with #my-dynamic-target' in the above example).

Browsers support

IE / EdgeFirefoxChromeSafariiOS SafariSamsung
85808413.112.212
1.4.1

4 years ago

1.4.0

4 years ago

1.3.0

4 years ago

1.1.2

4 years ago

1.1.1

4 years ago

1.1.0

5 years ago

1.0.8

5 years ago

1.0.7

5 years ago

1.0.5

5 years ago

1.0.3

5 years ago

1.0.2-2

5 years ago

1.0.2-1

5 years ago

1.0.2-0

5 years ago

1.0.1

5 years ago

1.0.0

5 years ago