Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allow promise-like objects as loadUtilsOnInit option #1878

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 1 addition & 4 deletions build/js/intlTelInput.js
Original file line number Diff line number Diff line change
Expand Up @@ -3099,10 +3099,7 @@ var factoryOutput = (() => {
);
} else if (typeof source === "function") {
try {
loadCall = source();
if (!(loadCall instanceof Promise)) {
throw new TypeError(`The function passed to loadUtils must return a promise for the utilities module, not ${typeof loadCall}`);
}
loadCall = Promise.resolve(source());
} catch (error) {
return Promise.reject(error);
}
Expand Down
2 changes: 1 addition & 1 deletion build/js/intlTelInput.min.js

Large diffs are not rendered by default.

5 changes: 1 addition & 4 deletions build/js/intlTelInputWithUtils.js
Original file line number Diff line number Diff line change
Expand Up @@ -3094,10 +3094,7 @@ var factoryOutput = (() => {
loadCall = Promise.reject(new Error("INTENTIONALLY BROKEN: this build of intl-tel-input includes the utilities module inline, but it has incorrectly attempted to load the utilities separately. If you are seeing this message, something is broken!"));
} else if (typeof source === "function") {
try {
loadCall = source();
if (!(loadCall instanceof Promise)) {
throw new TypeError(`The function passed to loadUtils must return a promise for the utilities module, not ${typeof loadCall}`);
}
loadCall = Promise.resolve(source());
} catch (error) {
return Promise.reject(error);
}
Expand Down
2 changes: 1 addition & 1 deletion build/js/intlTelInputWithUtils.min.js

Large diffs are not rendered by default.

5 changes: 1 addition & 4 deletions src/js/intl-tel-input.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2151,10 +2151,7 @@ const loadUtils = (source: string|UtilsLoader): Promise<unknown> | null => {
loadCall = import(/* webpackIgnore: true */ /* @vite-ignore */ source);
} else if (typeof source === "function") {
try {
loadCall = source();
if (!(loadCall instanceof Promise)) {
throw new TypeError(`The function passed to loadUtils must return a promise for the utilities module, not ${typeof loadCall}`);
}
loadCall = Promise.resolve(source());
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@jackocnr This seems fine to me. 👍 The main thing worth considering is that this will also allow the loadUtilsOnInit function to return the utils module object directly instead of just as a promise. That is, you can now do:

intlTelInput(inputElement, {
  // No promises involved!
  loadUtilsOnInit: () => ({
    default: { /* Locally defined utils module, or a mock, or whatever here */ }
  })
});

But that flexibility might be useful! So I think this is probably a good change. (Side note: the function can technically return anything with this change, but we have code later [line 2168] to validate that it at least vaguely looks like a JS module object, so that should be OK.)

OTOH, if you want to keep requiring that this returns a thennable (the more generic form of a JS promise), then the right canonical check would be something like:

loadCall = source();
if (typeof loadCall?.then !== 'function') {
  // Throw an error (or maybe return a rejection instead)
}

…but like I said, I think the added flexibility in this change as-is is probably better.

} catch (error) {
return Promise.reject(error);
}
Expand Down
19 changes: 19 additions & 0 deletions tests/options/loadUtilsOnInit.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,25 @@ describe("loadUtilsOnInit", () => {
expect(intlTelInput.utils).toBe(mockUtils.default);
});

it("works if loadUtilsOnInit returns a custom promise", async function() {
const mockUtils = { default: { mockUtils: true } };

const { iti } = initPlugin({
intlTelInput,
options: {
loadUtilsOnInit: () => ({
// eslint-disable-next-line @typescript-eslint/no-unused-vars
then: (resolve, reject) => resolve(mockUtils),
}),
},
});

expect(intlTelInput).toHaveProperty("startedLoadingUtilsScript", true);
await iti.promise;

expect(intlTelInput.utils).toBe(mockUtils.default);
});

describe("in 'withUtils' builds", () => {
const intlTelInput = require("intl-tel-input/intlTelInputWithUtils");
resetPackageAfterEach(intlTelInput);
Expand Down