kew: Lightweight Promise Library
kew is a lightweight promise/deferred library specifically designed for Node.js environments. Developed by Medium, its primary goal was to offer a high-performance alternative to the Q library, particularly for server-side applications experiencing CPU bottlenecks in chained database callbacks. Currently at version 0.7.0, the package appears to be unmaintained, with its last commit dating back several years, indicating an abandoned status and no active release cadence. It provides a subset of promise functionality, including methods like `Q.resolve()`, `Q.reject()`, `Q.defer()`, and promise chaining with `.then()` and `.fail()`. Unlike more comprehensive promise libraries, kew intentionally implements only the features necessary for the common server-side use cases identified by its original developers, prioritizing minimal footprint and speed.
Common errors
-
ReferenceError: Q is not defined
cause The `kew` library was not correctly imported or its export was not assigned to the `Q` variable.fixEnsure `const Q = require('kew');` is present and correctly scoped before `Q` is used. -
TypeError: kew is not a function
cause Attempting to invoke the `kew` module directly as a function (e.g., `new kew()`) instead of accessing its exported `Q` object.fixAccess the `Q` object after requiring the module: `const Q = require('kew'); const promise = Q.resolve('value');` -
SyntaxError: Cannot use import statement outside a module
cause Attempting to use ES module `import` syntax (e.g., `import Q from 'kew'`) in a Node.js CommonJS environment.fixUse the CommonJS `require` syntax: `const Q = require('kew');`
Warnings
- breaking kew implements only a subset of features found in other promise libraries like Q. Developers migrating from other promise libraries or expecting full Promise A+ compliance may encounter missing functionalities or different behaviors.
- gotcha The kew library is abandoned, with its last release (v0.7.0) several years ago. This means it receives no further updates, bug fixes, or security patches, making it unsuitable for new projects or critical production environments.
- gotcha kew is a CommonJS-only module and does not natively support ES Modules (ESM) `import`/`export` syntax. Attempting to use `import Q from 'kew'` directly in an ESM context will fail.
- gotcha kew predates modern JavaScript features like `async/await`. While its promises can interoperate with `async/await` if 'promisified' using utility functions (e.g., Node.js `util.promisify`), it does not offer direct support for these constructs, leading to less ergonomic code compared to native promises.
- gotcha The package does not ship with TypeScript declaration files (.d.ts). This makes it challenging to use in TypeScript projects without manually creating declaration files or resorting to `any` types.
Install
-
npm install kew -
yarn add kew -
pnpm add kew
Imports
- Q
import Q from 'kew'
const Q = require('kew') - defer
import { defer } from 'kew'const Q = require('kew'); const deferred = Q.defer(); - PromiseConstructor
import { Promise } from 'kew'const Q = require('kew'); const promise = Q.resolve('value');
Quickstart
const Q = require('kew');
// 1. Create a promise from a literal value
const successPromise = Q.resolve('Hello from kew!');
successPromise.then(function(message) {
console.log('Resolved with:', message);
});
// 2. Create a deferred promise and resolve it later
const myDeferred = Q.defer();
setTimeout(function() {
myDeferred.resolve('Delayed success!');
}, 500);
myDeferred.promise.then(function(result) {
console.log('Deferred resolved with:', result);
});
// 3. Handle node-style callbacks with makeNodeResolver
function getNodeStyleData(id, callback) {
setTimeout(() => {
if (id === 1) {
callback(null, { id: 1, name: 'Item 1' });
} else {
callback(new Error('Item not found!'));
}
}, 200);
}
const dataDefer = Q.defer();
getNodeStyleData(1, dataDefer.makeNodeResolver());
dataDefer.promise
.then(function(obj) {
console.log('Node-style callback success:', obj);
})
.fail(function(e) {
console.error('Node-style callback error:', e.message);
});
const errorDefer = Q.defer();
getNodeStyleData(2, errorDefer.makeNodeResolver());
errorDefer.promise
.then(function(obj) {
console.log('Node-style callback success (should not happen):', obj);
})
.fail(function(e) {
console.error('Node-style callback error (expected):', e.message);
});