Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

aldo-http

Package Overview
Dependencies
Maintainers
1
Versions
9
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

aldo-http - npm Package Compare versions

Comparing version 1.0.0-alpha.2 to 1.0.0-alpha.3

lib/response/base.d.ts

8

lib/factory.d.ts
/// <reference types="node" />
import * as https from 'https';
import { Server, RequestHandler } from './server';
export interface createServerOptions {
export declare type CreateServerOptions = {
tls?: https.ServerOptions;
}
};
/**

@@ -14,3 +14,3 @@ * Create a HTTP(S) Server

*/
export declare function createServer(options: createServerOptions, handler: RequestHandler): Server;
export declare function createServer(options: CreateServerOptions, handler: RequestHandler): Server;
/**

@@ -22,3 +22,3 @@ * Create a HTTP(S) Server

*/
export declare function createServer(options: createServerOptions): Server;
export declare function createServer(options: CreateServerOptions): Server;
/**

@@ -25,0 +25,0 @@ * Create a HTTP(S) Server

@@ -0,3 +1,3 @@

export * from './response';
export * from './factory';
export * from './server';
export * from './factory';
export * from './response';

@@ -6,4 +6,4 @@ "use strict";

Object.defineProperty(exports, "__esModule", { value: true });
__export(require("./response"));
__export(require("./factory"));
__export(require("./server"));
__export(require("./factory"));
__export(require("./response"));

@@ -5,18 +5,31 @@ /// <reference types="node" />

import * as https from 'https';
export declare type RequestHandler = (request: Request) => any;
export declare type RequestHandler = (req: IRequest) => any;
export declare type EventListener = (...args: any[]) => any;
export declare type Request = http.IncomingMessage;
export interface IRequest extends http.IncomingMessage {
}
/**
* High level server for request handling
*/
export declare class Server {
native: http.Server | https.Server;
/**
* Initialize a `Server` instance
* The internal server
*
* @param native The native HTTP(S) server
* @protected
*/
constructor(native: http.Server | https.Server);
protected _server: http.Server | https.Server;
/**
* Add a request handler
* Create a new server instance
*
* @param server The HTTP(S) native server
* @constructor
* @public
*/
constructor(server: http.Server | https.Server);
/**
* Add a handler for the `request` event
*
* @param event The `request` event
* @param handler The `request` handler
* @public
*/
on(event: 'request', handler: RequestHandler): this;

@@ -27,7 +40,31 @@ /**

* @param event The event name
* @param listener The event listener
* @public
*/
on(event: string, listener: EventListener): this;
/**
* Add a one time `listener` for the given `event`
*
* @param event The event name
* @param fn The event listener
* @public
*/
on(event: string, fn: EventListener): this;
once(event: string, fn: EventListener): this;
/**
* Trigger the `event` with `args`
*
* @param event The event name
* @param args The optional arguments to pass
* @public
*/
emit(event: string, ...args: any[]): boolean;
/**
* Stop listening to the given `event`
*
* @param event The event name
* @param fn The event listener
* @public
*/
off(event?: string, fn?: EventListener): this;
/**
* Start a server listening for requests

@@ -45,8 +82,8 @@ *

/**
* Wrap the request event listener
* Wrap the request handler
*
* @param handler The request event listener
* @private
* @param handler The request handler
* @protected
*/
private _wrap(handler);
protected _wrap(handler: EventListener): EventListener;
}
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const is_1 = require("@sindresorhus/is");
const timers_1 = require("timers");
const response_1 = require("./response");
/**
* High level server for request handling
*/
class Server {
/**
* Initialize a `Server` instance
* Create a new server instance
*
* @param native The native HTTP(S) server
* @param server The HTTP(S) native server
* @constructor
* @public
*/
constructor(native) {
this.native = native;
constructor(server) {
this._server = server;
}
on(event, handler) {
on(event, fn) {
if (event === 'request')
handler = this._wrap(handler);
this.native.on(event, _defer(handler));
fn = this._wrap(fn);
// attach the listener
this._server.on(event, _defer(fn));
return this;
}
/**
* Add a one time `listener` for the given `event`
*
* @param event The event name
* @param fn The event listener
* @public
*/
once(event, fn) {
this._server.once(event, _defer(fn));
return this;
}
/**
* Trigger the `event` with `args`
*
* @param event The event name
* @param args The optional arguments to pass
* @public
*/
emit(event, ...args) {
return this._server.emit(event, ...args);
}
/**
* Stop listening to the given `event`
*
* @param event The event name
* @param fn The event listener
* @public
*/
off(event, fn) {
if (event == null || fn == null) {
this._server.removeAllListeners(event);
}
else {
this._server.removeListener(event, fn);
}
return this;
}
/**
* Start a server listening for requests

@@ -27,9 +69,12 @@ *

start(portOrOptions) {
// attach a default error handler
if (!this._server.listenerCount('error'))
this.on('error', _onError);
return new Promise((resolve, reject) => {
// attach the error listener
this.native.once('error', reject);
this._server.once('error', reject);
// listening
this.native.listen(portOrOptions, () => {
this._server.listen(portOrOptions, () => {
// remove the unecessary error listener
this.native.removeListener('error', reject);
this._server.removeListener('error', reject);
// resolve the promise

@@ -47,14 +92,19 @@ resolve();

return new Promise((resolve, reject) => {
this.native.close((e) => e ? reject(e) : resolve());
this._server.close((e) => e ? reject(e) : resolve());
});
}
/**
* Wrap the request event listener
* Wrap the request handler
*
* @param handler The request event listener
* @private
* @param handler The request handler
* @protected
*/
_wrap(handler) {
return (req, res) => {
new Promise((resolve) => resolve(handler(req))).catch((err) => {
return async (req, res) => {
try {
let output = await handler(req);
let response = response_1.createResponse(output);
await response.send(res);
}
catch (err) {
// normalize

@@ -64,20 +114,12 @@ if (!(err instanceof Error)) {

}
// delegate
this.native.emit('error', err);
let status = err.status || err.statusCode;
let body = err.expose ? err.message : 'Internal Server Error';
// support ENOENT
if (err.code === 'ENOENT')
status = 404;
return new response_1.Response(body)
.status(_isValid(status) ? status : 500)
.type('text/plain; charset=utf-8')
.set(err.headers || {});
})
.then((response) => {
if (!(response instanceof response_1.Response)) {
response = new response_1.Response(response);
if (err.code === 'ENOENT') {
err.expose = true;
err.status = 404;
}
response.send(res);
});
// send
response_1.createErrorResponse(err).send(res);
// delegate
this.emit('error', err);
}
};

@@ -88,18 +130,23 @@ }

/**
* Defer the function invocation to the next tick
* The default `error` event listener
*
* @param fn The event listener
* @param err The error object
* @private
*/
function _defer(fn) {
return (...args) => timers_1.setImmediate(fn, ...args);
function _onError(err) {
if (err.status === 404 || err.expose)
return;
let msg = err.stack || err.toString();
console.error();
console.error(msg.replace(/^/gm, ' '));
console.error();
}
/**
* Check if the status code is a valid number
* Defer the function invocation to the next tick
*
* @param status
* @param fn The event listener
* @private
*/
function _isValid(status) {
return typeof status === 'number' && status >= 100 && status <= 999;
function _defer(fn) {
return (...args) => setImmediate(fn, ...args);
}
{
"name": "aldo-http",
"version": "1.0.0-alpha.2",
"version": "1.0.0-alpha.3",
"description": "Enhanced HTTP `createServer` module for Node.js",

@@ -16,3 +16,3 @@ "types": "lib/index.d.ts",

"build": "tsc",
"prepublishOnly": "tsc && npm test && npm test",
"prepublishOnly": "tsc && npm test",
"test": "mocha -R dot -r ts-node/register \"test/**/*.ts\""

@@ -43,3 +43,2 @@ },

"@types/sinon": "^4.3.0",
"@types/statuses": "^1.3.0",
"mocha": "^5.0.0",

@@ -52,5 +51,4 @@ "sinon": "^4.4.2",

"@sindresorhus/is": "^0.9.0",
"mime-types": "^2.1.18",
"statuses": "^1.5.0"
"mime-types": "^2.1.18"
}
}

@@ -56,3 +56,3 @@

Each handler will receive the `http.IncomingMessage` object as a single input, and could return anything as a response.
Each handler will receive the `http.IncomingMessage` object as a request, and could return anything as a response.

@@ -69,7 +69,7 @@ ```ts

To get more control over the response to send, [Response](#response) instances could be returned.
To get more control over the response to send, [Response](#response) instances could be used.
## Response
The response instance let you construct a complex response (status code, body and headers)
The response instance let you construct a complex response with status code, body and headers.

@@ -85,19 +85,41 @@ ```ts

type(value: string): this;
etag(value: string): this;
length(value: number): this;
location(url: string): this;
has(header: string): boolean;
remove(header: string): this;
setCookie(value: string): this;
vary(...headers: string[]): this;
send(res: http.ServerResponse): void;
lastModified(value: string | Date): this;
status(code: number, message?: string): this;
append(header: string, value: string | string[]): this;
get(header: string): string | number | string[] | undefined;
set(header: string, value: string | number | string[]): this;
set(headers: { [field: string]: string | number | string[]; }): this;
reset(headers?: { [field: string]: string | number | string[]; }): this;
type(value: string): this; // set the `Content-Type` header
etag(value: string): this; // set the `ETag` header
length(value: number): this; // set the `Content-Length` header
location(url: string): this; // set the `Location` header
has(header: string): boolean; // check the given header is already set
remove(header: string): this; // remove the give header
setCookie(value: string): this; // append a `Set-Cookie` header
vary(...headers: string[]): this; // append a `Vary` header
send(res: http.ServerResponse): void; // send the response to the client (used internally)
lastModified(value: string | Date): this; // set the `Last-Modfied` header
status(code: number, message?: string): this; // set the status code and message
append(header: string, value: string | string[]): this; // append a header value
get(header: string): string | number | string[] | undefined; // get the header value
set(header: string, value: string | number | string[]): this; // set the header value
set(headers: { [field: string]: string | number | string[]; }): this; // set multiple headers
reset(headers?: { [field: string]: string | number | string[]; }): this; // reset the headers
}
```
To create [Response](#response) instances, you may use the `constructor` or one of the available factories:
- `createRespnse(content?)` to create a response based on the given content.
- `createEmptyResponse()` to create an empty response (default status code `204`).
- `createHtmlResponse(html)` to create a HTML response, sets the `Content-Type` header to `text/html; charset=utf-8` and the `Content-Length` header.
- `createTextResponse(text)` to create a text response, sets the `Content-Type` header to `text/plain; charset=utf-8` and the `Content-Length` header.
- `createBufferResponse(buff)` to create a buffered response, sets the `Content-Type` header to `application/octet-stream` and the `Content-Length` header.
- `createStreamResponse(stream)` to create a streamed response, sets the `Content-Type` header to `application/octet-stream`.
- `createJsonResponse(object)` to create a JSON response, sets the `Content-Type` header to `application/json; charset=utf-8` and the `Content-Length` header.
```js
const { createServer, createTextResponse } = require('aldo-http')
// handler
const handler = () => createTextResponse("Hello world!")
// server
const server = createServer(handler)
// start
server.start(3000)
```
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc