construct,
} = Reflect;
+/**
+ * Returns whether calling the provided function with no `this` value
+ * or arguments completes normally; that is, does not throw an error.
+ *
+ * ☡ This function will throw an error if the provided argument is not
+ * callable.
+ */
+export const completesNormally = ($) => {
+ if (!isCallable($)) {
+ // The provided value is not callable; this is an error.
+ throw new TypeError(
+ `Piscēs: Cannot determine completion of noncallable value: ${$}`,
+ );
+ } else {
+ // The provided value is callable.
+ try {
+ // Attempt to call the function and return true if this succeeds.
+ $();
+ return true;
+ } catch {
+ // Calling the function did not succeed; return false.
+ return false;
+ }
+ }
+};
+
/**
* Returns the provided value.
*
import {
assertEquals,
assertStrictEquals,
+ assertThrows,
describe,
it,
} from "./dev-deps.js";
import {
bind,
call,
+ completesNormally,
construct,
identity,
isCallable,
});
});
+describe("completesNormally", () => {
+ it("[[Call]] returns true for functions which complete normally", () => {
+ assertStrictEquals(completesNormally(() => {}), true);
+ });
+
+ it("[[Call]] returns false for functions which throw", () => {
+ assertStrictEquals(
+ completesNormally(() => {
+ throw null;
+ }),
+ false,
+ );
+ });
+
+ it("[[Call]] throws when the argument is not callable", () => {
+ assertThrows(() => {
+ completesNormally(null);
+ });
+ });
+
+ it("[[Call]] throws when the argument is not provided", () => {
+ assertThrows(() => {
+ completesNormally();
+ });
+ });
+});
+
describe("construct", () => {
it("[[Call]] defaults to the constructor as the target", () => {
const constructor = class {};