Skip to content
This repository has been archived by the owner on Aug 31, 2024. It is now read-only.

update: ready to next release #13

Merged
merged 10 commits into from
Sep 10, 2020
Merged
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
19 changes: 19 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1 +1,20 @@

# OS #
###################
.DS_Store
.idea
Thumbs.db
tmp
temp


# Node.js #
###################
node_modules
package-lock.json


# NYC #
###################
coverage
.nyc_output
15 changes: 15 additions & 0 deletions .nycrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
{
"extension": [
".js"
],
"exclude": [
"index.spec.js"
],
"reporter": [
"text-lcov",
"text",
"lcov"
],
"report-dir": "./coverage",
"temp-dir": "./.nyc_output"
}
8 changes: 5 additions & 3 deletions .travis.yml
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
language: node_js
node_js:
- "4"
- "5"
script: "npm run test"
- 10
- 12
- 14
script:
- npm run ci
2 changes: 1 addition & 1 deletion LICENSE
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
The MIT License (MIT)

Copyright (c) 2015 yunsong
Copyright (c) 2020 Koa.js contributors

Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
Expand All @@ -19,4 +20,3 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

43 changes: 34 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,12 +1,34 @@

# koa-convert

[![npm version](https://img.shields.io/npm/v/koa-convert.svg)](https://npmjs.org/package/koa-convert)
[![build status](https://travis-ci.org/koajs/convert.svg)](https://travis-ci.org/koajs/convert)
[![Build Status][travis-img]][travis-url]
[![NPM version][npm-badge]][npm-url]
[![License][license-badge]][license-url]
![Code Size][code-size-badge]

<!-- [![Coverage Status][coverage-img]][coverage-url] -->

<!-- ***************** -->

[travis-img]: https://travis-ci.org/koajs/convert.svg?branch=master
[travis-url]: https://travis-ci.org/koajs/convert

Convert koa legacy ( 0.x & 1.x ) generator middleware to modern promise middleware ( 2.x ).
<!--
WAIT FOR ACCESS
[coverage-img]: https://coveralls.io/repos/github/koajs/convert/badge.svg?branch=master
[coverage-url]: https://coveralls.io/github/koajs/convert?branch=master
-->

It could also convert modern promise middleware back to legacy generator middleware ( useful to help modern middleware support koa 0.x or 1.x ).
[npm-badge]: https://img.shields.io/npm/v/koa-better-request-id.svg?style=flat
[npm-url]: https://www.npmjs.com/package/koa-better-request-id
[license-badge]: https://img.shields.io/badge/license-MIT-green.svg?style=flat-square
[license-url]: https://github.com/koajs/koa-convert/blob/master/LICENSE
[code-size-badge]: https://img.shields.io/github/languages/code-size/koajs/koa-convert

<!-- ***************** -->

Convert Koa legacy (0.x & 1.x) generator middleware to modern promise middleware (2.x).

It could also convert modern promise middleware back to legacy generator middleware (useful to help modern middleware support Koa v0.x or v1.x).

## Note

Expand All @@ -21,8 +43,11 @@ You may use following packages for [routing](https://github.com/koajs/koa/wiki#r

## Installation

```
$ npm install koa-convert
```bash
# npm ..
$ npm i koa-convert
# yarn ..
$ yarn add koa-convert
```

## Usage
Expand Down Expand Up @@ -54,7 +79,7 @@ function modernMiddleware (ctx, next) {

## Distinguish legacy and modern middleware

In koa 0.x and 1.x ( without experimental flag ), `app.use` has an assertion that all ( legacy ) middleware must be generator function and it's tested with `fn.constructor.name == 'GeneratorFunction'` at [here](https://github.com/koajs/koa/blob/7fe29d92f1e826d9ce36029e1b9263b94cba8a7c/lib/application.js#L105).
In koa 0.x and 1.x (without experimental flag), `app.use` has an assertion that all (legacy) middleware must be generator function and it's tested with `fn.constructor.name == 'GeneratorFunction'` at [here](https://github.com/koajs/koa/blob/7fe29d92f1e826d9ce36029e1b9263b94cba8a7c/lib/application.js#L105).

Therefore, we can distinguish legacy and modern middleware with `fn.constructor.name == 'GeneratorFunction'`.

Expand Down Expand Up @@ -138,4 +163,4 @@ legacyMiddleware = convert.back(modernMiddleware)

## License

MIT
[MIT](LICENSE)
71 changes: 58 additions & 13 deletions index.js
Original file line number Diff line number Diff line change
@@ -1,60 +1,105 @@
'use strict'

/**
* Module dependencies.
*/

const co = require('co')
const compose = require('koa-compose')

/**
* Expose `convert()`.
*/

module.exports = convert

/**
* Convert Koa legacy generator-based middleware
* to modern promise-based middleware.
*
*
* @api public
* */

function convert (mw) {
if (typeof mw !== 'function') {
throw new TypeError('middleware must be a function')
}
if (mw.constructor.name !== 'GeneratorFunction') {
// assume it's Promise-based middleware

// assume it's Promise-based middleware
if (
mw.constructor.name !== 'GeneratorFunction' &&
mw.constructor.name !== 'AsyncGeneratorFunction'
) {
return mw
}

const converted = function (ctx, next) {
return co.call(ctx, mw.call(ctx, createGenerator(next)))
return co.call(
ctx,
mw.call(
ctx,
(function * (next) { return yield next() })(next)
))
}

converted._name = mw._name || mw.name
return converted
}

function * createGenerator (next) {
return yield next()
}
/**
* Convert and compose multiple middleware
* (could mix legacy and modern ones)
* and return modern promise middleware.
*
*
* @api public
* */

// convert.compose(mw, mw, mw)
// convert.compose([mw, mw, mw])
convert.compose = function (arr) {
if (!Array.isArray(arr)) {
arr = Array.from(arguments)
}

return compose(arr.map(convert))
}

/**
* Convert Koa modern promise-based middleware
* to legacy generator-based middleware.
*
*
* @api public
* */

convert.back = function (mw) {
if (typeof mw !== 'function') {
throw new TypeError('middleware must be a function')
}
if (mw.constructor.name === 'GeneratorFunction') {
// assume it's generator middleware

// assume it's generator middleware
if (mw.constructor.name === 'GeneratorFunction' || mw.constructor.name === 'AsyncGeneratorFunction') {
return mw
}

const converted = function * (next) {
let ctx = this
const ctx = this
let called = false
// no need try...catch here, it's ok even `mw()` throw exception
yield Promise.resolve(mw(ctx, function () {

yield mw(ctx, function () {
if (called) {
// guard against multiple next() calls
// https://github.com/koajs/compose/blob/4e3e96baf58b817d71bd44a8c0d78bb42623aa95/index.js#L36
return Promise.reject(new Error('next() called multiple times'))
throw new Error('next() called multiple times')
}

called = true
return co.call(ctx, next)
}))
})
}

converted._name = mw._name || mw.name
return converted
}
Loading