mirror of
https://github.com/shimataro/ssh-key-action.git
synced 2025-06-19 22:52:10 +10:00
* first action! (#1)
This commit is contained in:
parent
8deacc95b1
commit
ace1e6a69a
3750 changed files with 1155519 additions and 0 deletions
66
node_modules/protoduck/CHANGELOG.md
generated
vendored
Normal file
66
node_modules/protoduck/CHANGELOG.md
generated
vendored
Normal file
|
@ -0,0 +1,66 @@
|
|||
# Change Log
|
||||
|
||||
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
|
||||
|
||||
<a name="5.0.1"></a>
|
||||
## [5.0.1](https://github.com/zkat/protoduck/compare/v5.0.0...v5.0.1) (2018-10-26)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **security:** npm audit fix ([55a2007](https://github.com/zkat/protoduck/commit/55a2007))
|
||||
* **standard:** standard --fix ([2dedbb8](https://github.com/zkat/protoduck/commit/2dedbb8))
|
||||
|
||||
|
||||
|
||||
<a name="5.0.0"></a>
|
||||
# [5.0.0](https://github.com/zkat/protoduck/compare/v4.0.0...v5.0.0) (2017-12-12)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **license:** relicense to MIT ([55cdd89](https://github.com/zkat/protoduck/commit/55cdd89))
|
||||
* **platforms:** drop support for node 4 and 7 ([07a19b1](https://github.com/zkat/protoduck/commit/07a19b1))
|
||||
|
||||
|
||||
### BREAKING CHANGES
|
||||
|
||||
* **platforms:** node 4 and node 7 are no longer officially supported
|
||||
* **license:** license changed from CC0-1.0 to MIT
|
||||
|
||||
|
||||
|
||||
<a name="4.0.0"></a>
|
||||
# [4.0.0](https://github.com/zkat/protoduck/compare/v3.3.2...v4.0.0) (2017-04-17)
|
||||
|
||||
|
||||
### Bug Fixes
|
||||
|
||||
* **test:** .name is inconsistently available ([3483f4a](https://github.com/zkat/protoduck/commit/3483f4a))
|
||||
|
||||
|
||||
### Features
|
||||
|
||||
* **api:** Fresh New API™ ([#2](https://github.com/zkat/protoduck/issues/2)) ([534e5cf](https://github.com/zkat/protoduck/commit/534e5cf))
|
||||
* **constraints:** added optional where-constraints ([16ad124](https://github.com/zkat/protoduck/commit/16ad124))
|
||||
* **defaults:** allow default impls without arrays in defs ([6cf7d84](https://github.com/zkat/protoduck/commit/6cf7d84))
|
||||
* **deps:** use genfun[@4](https://github.com/4) ([f6810a7](https://github.com/zkat/protoduck/commit/f6810a7))
|
||||
* **meta:** bringing project stuff up to date ([61791da](https://github.com/zkat/protoduck/commit/61791da))
|
||||
|
||||
|
||||
### BREAKING CHANGES
|
||||
|
||||
* **api:** The API was significantly overhauled.
|
||||
|
||||
* New protocol creating is now through protoduck.define() instead of protoduck()
|
||||
* Implementations are through Duck#impl instead of Duck(...)
|
||||
* The `private` option was removed
|
||||
* Static protocols were removed -- only method-style protocols are available now.
|
||||
* As part of that: the target argument to impl can no longer be omitted
|
||||
* The main export object is now the metaobject. protoduck.impl can be used to extend to MOP
|
||||
* .isDerivable is now a property on Duck instances, not a static method
|
||||
* .hasImpl is now a method on Duck instances, not a static method
|
||||
* Protoduck will now genfunnify existing functions as default methods for genfuns declared in a protocol when implementing
|
||||
* Error messages have been overhauled to be more helpful
|
||||
* **deps:** nextMethod is now an extra argument to methods
|
||||
* **meta:** node@<4 is no longer supported
|
21
node_modules/protoduck/LICENSE
generated
vendored
Normal file
21
node_modules/protoduck/LICENSE
generated
vendored
Normal file
|
@ -0,0 +1,21 @@
|
|||
The MIT License (MIT)
|
||||
Copyright (c) 2017 Kat Marchán
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
||||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
||||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
|
||||
IN NO EVENT SHALL THE 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.
|
||||
|
346
node_modules/protoduck/README.md
generated
vendored
Normal file
346
node_modules/protoduck/README.md
generated
vendored
Normal file
|
@ -0,0 +1,346 @@
|
|||
# protoduck [](https://npm.im/protoduck) [](https://npm.im/protoduck) [](https://travis-ci.org/zkat/protoduck) [](https://ci.appveyor.com/project/zkat/protoduck) [](https://coveralls.io/github/zkat/protoduck?branch=latest)
|
||||
|
||||
[`protoduck`](https://github.com/zkat/protoduck) is a JavaScript library is a
|
||||
library for making groups of methods, called "protocols".
|
||||
|
||||
If you're familiar with the concept of ["duck
|
||||
typing"](https://en.wikipedia.org/wiki/Duck_typing), then it might make sense to
|
||||
think of protocols as things that explicitly define what methods you need in
|
||||
order to "clearly be a duck".
|
||||
|
||||
## Install
|
||||
|
||||
`$ npm install -S protoduck`
|
||||
|
||||
## Table of Contents
|
||||
|
||||
* [Example](#example)
|
||||
* [Features](#features)
|
||||
* [Guide](#guide)
|
||||
* [Introduction](#introduction)
|
||||
* [Defining protocols](#defining-protocols)
|
||||
* [Implementations](#protocol-impls)
|
||||
* [Multiple dispatch](#multiple-dispatch)
|
||||
* [Constraints](#constraints)
|
||||
* [API](#api)
|
||||
* [`define()`](#define)
|
||||
* [`proto.impl()`](#impl)
|
||||
|
||||
### Example
|
||||
|
||||
```javascript
|
||||
const protoduck = require('protoduck')
|
||||
|
||||
// Quackable is a protocol that defines three methods
|
||||
const Quackable = protoduck.define({
|
||||
walk: [],
|
||||
talk: [],
|
||||
isADuck: [() => true] // default implementation -- it's optional!
|
||||
})
|
||||
|
||||
// `duck` must implement `Quackable` for this function to work. It doesn't
|
||||
// matter what type or class duck is, as long as it implements Quackable.
|
||||
function doStuffToDucks (duck) {
|
||||
if (!duck.isADuck()) {
|
||||
throw new Error('I want a duck!')
|
||||
} else {
|
||||
console.log(duck.walk())
|
||||
console.log(duck.talk())
|
||||
}
|
||||
}
|
||||
|
||||
// ...In a different package:
|
||||
const ducks = require('./ducks')
|
||||
|
||||
class Duck () {}
|
||||
|
||||
// Implement the protocol on the Duck class.
|
||||
ducks.Quackable.impl(Duck, {
|
||||
walk () { return "*hobble hobble*" }
|
||||
talk () { return "QUACK QUACK" }
|
||||
})
|
||||
|
||||
// main.js
|
||||
ducks.doStuffToDucks(new Duck()) // works!
|
||||
```
|
||||
|
||||
### Features
|
||||
|
||||
* Verifies implementations in case methods are missing or wrong ones added
|
||||
* Helpful, informative error messages
|
||||
* Optional default method implementations
|
||||
* Fresh JavaScript Feel™ -- methods work just like native methods when called
|
||||
* Methods can dispatch on arguments, not just `this` ([multimethods](https://npm.im/genfun))
|
||||
* Type constraints
|
||||
|
||||
### Guide
|
||||
|
||||
#### Introduction
|
||||
|
||||
Like most Object-oriented languages, JavaScript comes with its own way of
|
||||
defining methods: You simply add regular `function`s as properties to regular
|
||||
objects, and when you do `obj.method()`, it calls the right code! ES6/ES2015
|
||||
further extended this by adding a `class` syntax that allowed this same system
|
||||
to work with more familiar syntax sugar: `class Foo { method() { ... } }`.
|
||||
|
||||
The point of "protocols" is to have a more explicit definitions of what methods
|
||||
"go together". That is, a protocol is a description of a type of object your
|
||||
code interacts with. If someone passes an object into your library, and it fits
|
||||
your defined protocol, the assumption is that the object will work just as well.
|
||||
|
||||
Duck typing is a common term for this sort of thing: If it walks like a duck,
|
||||
and it talks like a duck, then it may as well be a duck, as far as any of our
|
||||
code is concerned.
|
||||
|
||||
Many other languages have similar or identical concepts under different names:
|
||||
Java's interfaces, Haskell's typeclasses, Rust's traits. Elixir and Clojure both
|
||||
call them "protocols" as well.
|
||||
|
||||
One big advantage to using these protocols is that they let users define their
|
||||
own versions of some abstraction, without requiring the type to inherit from
|
||||
another -- protocols are independent of inheritance, even though they're able to
|
||||
work together with it. If you've ever found yourself in some sort of inheritance
|
||||
mess, this is exactly the sort of thing you use to escape it.
|
||||
|
||||
#### Defining Protocols
|
||||
|
||||
The first step to using `protoduck` is to define a protocol. Protocol
|
||||
definitions look like this:
|
||||
|
||||
```javascript
|
||||
// import the library first!
|
||||
const protoduck = require('protoduck')
|
||||
|
||||
// `Ducklike` is the name of our protocol. It defines what it means for
|
||||
// something to be "like a duck", as far as our code is concerned.
|
||||
const Ducklike = protoduck.define([], {
|
||||
walk: [], // This says that the protocol requires a "walk" method.
|
||||
talk: [] // and ducks also need to talk
|
||||
peck: [] // and they can even be pretty scary
|
||||
})
|
||||
```
|
||||
|
||||
Protocols by themselves don't really *do* anything, they simply define what
|
||||
methods are included in the protocol, and thus what will need to be implemented.
|
||||
|
||||
#### Protocol Impls
|
||||
|
||||
The simplest type of definitions for protocols are as regular methods. In this
|
||||
style, protocols end up working exactly like normal JavaScript methods: they're
|
||||
added as properties of the target type/object, and we call them using the
|
||||
`foo.method()` syntax. `this` is accessible inside the methods, as usual.
|
||||
|
||||
Implementation syntax is very similar to protocol definitions, using `.impl`:
|
||||
|
||||
```javascript
|
||||
class Dog {}
|
||||
|
||||
// Implementing `Ducklike` for `Dog`s
|
||||
Ducklike.impl(Dog, [], {
|
||||
walk () { return '*pads on all fours*' }
|
||||
talk () { return 'woof woof. I mean "quack" >_>' }
|
||||
peck (victim) { return 'Can I just bite ' + victim + ' instead?...' }
|
||||
})
|
||||
```
|
||||
|
||||
So now, our `Dog` class has two extra methods: `walk`, and `talk`, and we can
|
||||
just call them:
|
||||
|
||||
```javascript
|
||||
const pupper = new Dog()
|
||||
|
||||
pupper.walk() // *pads on all fours*
|
||||
pupper.talk() // woof woof. I mean "quack" >_>
|
||||
pupper.peck('this string') // Can I just bite this string instead?...
|
||||
```
|
||||
|
||||
#### Multiple Dispatch
|
||||
|
||||
You may have noticed before that we have these `[]` in various places that don't
|
||||
seem to have any obvious purpose.
|
||||
|
||||
These arrays allow protocols to be implemented not just for a single value of
|
||||
`this`, but across *all arguments*. That is, you can have methods in these
|
||||
protocols that use both `this`, and the first argument (or any other arguments)
|
||||
in order to determine what code to actually execute.
|
||||
|
||||
This type of method is called a multimethod, and is one of the differences
|
||||
between protoduck and the default `class` syntax.
|
||||
|
||||
To use it: in the protocol *definitions*, you put matching
|
||||
strings in different spots where those empty arrays were, and when you
|
||||
*implement* the protocol, you give the definition the actual types/objects you
|
||||
want to implement it on, and it takes care of mapping types to the strings you
|
||||
defined, and making sure the right code is run:
|
||||
|
||||
```javascript
|
||||
const Playful = protoduck.define(['friend'], {// <---\
|
||||
playWith: ['friend'] // <------------ these correspond to each other
|
||||
})
|
||||
|
||||
class Cat {}
|
||||
class Human {}
|
||||
class Dog {}
|
||||
|
||||
// The first protocol is for Cat/Human combination
|
||||
Playful.impl(Cat, [Human], {
|
||||
playWith (human) {
|
||||
return '*headbutt* *purr* *cuddle* omg ilu, ' + human.name
|
||||
}
|
||||
})
|
||||
|
||||
// And we define it *again* for a different combination
|
||||
Playful.impl(Cat, [Dog], {
|
||||
playWith (dog) {
|
||||
return '*scratches* *hisses* omg i h8 u, ' + dog.name
|
||||
}
|
||||
})
|
||||
|
||||
// depending on what you call it with, it runs different methods:
|
||||
const cat = new Cat()
|
||||
const human = new Human()
|
||||
const dog = new Dog()
|
||||
|
||||
cat.playWith(human) // *headbutt* *purr* *cuddle* omg ilu, Sam
|
||||
cat.playWith(dog) // *scratches* *hisses* omg i h8 u, Pupper
|
||||
```
|
||||
|
||||
#### Constraints
|
||||
|
||||
Sometimes, you want to have all the functionality of a certain protocol, but you
|
||||
want to add a few requirements or other bits an pieces. Usually, you would have
|
||||
to define the entire functionality of the "parent" protocol in your own protocol
|
||||
in order to pull this off. This isn't very DRY and thus prone to errors, missing
|
||||
or out-of-sync functionality, or other issues. You could also just tell users
|
||||
"hey, if you implement this, make sure to implement that", but there's no
|
||||
guarantee they'll know about it, or know which arguments map to what.
|
||||
|
||||
This is where constraints come in: You can define a protocol that expects
|
||||
anything that implements it to *also* implement one or more "parent" protocols.
|
||||
|
||||
```javascript
|
||||
const Show = proto.define({
|
||||
// This syntax allows default impls without using arrays.
|
||||
toString () {
|
||||
return Object.prototype.toString.call(this)
|
||||
},
|
||||
toJSON () {
|
||||
return JSON.stringify(this)
|
||||
}
|
||||
})
|
||||
|
||||
const Log = proto.define({
|
||||
log () { console.log(this.toString()) }
|
||||
}, {
|
||||
where: Show()
|
||||
// Also valid:
|
||||
// [Show('this'), Show('a')]
|
||||
// [Show('this', ['a', 'b'])]
|
||||
})
|
||||
|
||||
// This fails with an error: must implement Show:
|
||||
Log.impl(MyThing)
|
||||
|
||||
// So derive Show first...
|
||||
Show.impl(MyThing)
|
||||
// And now it's ok!
|
||||
Log.impl(MyThing)
|
||||
```
|
||||
|
||||
### API
|
||||
|
||||
#### <a name="define"></a> `define(<types>?, <spec>, <opts>)`
|
||||
|
||||
Defines a new protocol on across arguments of types defined by `<types>`, which
|
||||
will expect implementations for the functions specified in `<spec>`.
|
||||
|
||||
If `<types>` is missing, it will be treated the same as if it were an empty
|
||||
array.
|
||||
|
||||
The types in `<spec>` entries must map, by string name, to the type names
|
||||
specified in `<types>`, or be an empty array if `<types>` is omitted. The types
|
||||
in `<spec>` will then be used to map between method implementations for the
|
||||
individual functions, and the provided types in the impl.
|
||||
|
||||
Protocols can include an `opts` object as the last argument, with the following
|
||||
available options:
|
||||
|
||||
* `opts.name` `{String}` - The name to use when referring to the protocol.
|
||||
|
||||
* `opts.where` `{Array[Constraint]|Constraint}` - Protocol constraints to use.
|
||||
|
||||
* `opts.metaobject` - Accepts an object implementing the
|
||||
`Protoduck` protocol, which can be used to alter protocol definition
|
||||
mechanisms in `protoduck`.
|
||||
|
||||
##### Example
|
||||
|
||||
```javascript
|
||||
const Eq = protoduck.define(['a'], {
|
||||
eq: ['a']
|
||||
})
|
||||
```
|
||||
|
||||
#### <a name="impl"></a> `proto.impl(<target>, <types>?, <implementations>?)`
|
||||
|
||||
Adds a new implementation to the given protocol across `<types>`.
|
||||
|
||||
`<implementations>` must be an object with functions matching the protocol's
|
||||
API. If given, the types in `<types>` will be mapped to their corresponding
|
||||
method arguments according to the original protocol definition.
|
||||
|
||||
If a protocol is derivable -- that is, all its functions have default impls,
|
||||
then the `<implementations>` object can be omitted entirely, and the protocol
|
||||
will be automatically derived for the given `<types>`
|
||||
|
||||
##### Example
|
||||
|
||||
```javascript
|
||||
import protoduck from 'protoduck'
|
||||
|
||||
// Singly-dispatched protocols
|
||||
const Show = protoduck.define({
|
||||
show: []
|
||||
})
|
||||
|
||||
class Foo {
|
||||
constructor (name) {
|
||||
this.name = name
|
||||
}
|
||||
}
|
||||
|
||||
Show.impl(Foo, {
|
||||
show () { return `[object Foo(${this.name})]` }
|
||||
})
|
||||
|
||||
const f = new Foo('alex')
|
||||
f.show() === '[object Foo(alex)]'
|
||||
```
|
||||
|
||||
```javascript
|
||||
import protoduck from 'protoduck'
|
||||
|
||||
// Multi-dispatched protocols
|
||||
const Comparable = protoduck.define(['target'], {
|
||||
compare: ['target'],
|
||||
})
|
||||
|
||||
class Foo {}
|
||||
class Bar {}
|
||||
class Baz {}
|
||||
|
||||
Comparable.impl(Foo, [Bar], {
|
||||
compare (bar) { return 'bars are ok' }
|
||||
})
|
||||
|
||||
Comparable.impl(Foo, [Baz], {
|
||||
compare (baz) { return 'but bazzes are better' }
|
||||
})
|
||||
|
||||
const foo = new Foo()
|
||||
const bar = new Bar()
|
||||
const baz = new Baz()
|
||||
|
||||
foo.compare(bar) // 'bars are ok'
|
||||
foo.compare(baz) // 'but bazzes are better'
|
||||
```
|
349
node_modules/protoduck/index.js
generated
vendored
Normal file
349
node_modules/protoduck/index.js
generated
vendored
Normal file
|
@ -0,0 +1,349 @@
|
|||
'use strict'
|
||||
|
||||
const genfun = require('genfun')
|
||||
|
||||
class Duck extends Function {
|
||||
// Duck.impl(Foo, [String, Array], { frob (str, arr) { ... }})
|
||||
impl (target, types, impls) {
|
||||
if (!impls && !isArray(types)) {
|
||||
impls = types
|
||||
types = []
|
||||
}
|
||||
if (!impls && this.isDerivable) {
|
||||
impls = this._defaultImpls
|
||||
}
|
||||
if (!impls) {
|
||||
impls = {}
|
||||
}
|
||||
if (typeof target === 'function' && !target.isGenfun) {
|
||||
target = target.prototype
|
||||
}
|
||||
checkImpls(this, target, impls)
|
||||
checkArgTypes(this, types)
|
||||
this._constraints.forEach(c => {
|
||||
if (!c.verify(target, types)) {
|
||||
throw new Error(`Implementations of ${
|
||||
this.name || 'this protocol'
|
||||
} must first implement ${
|
||||
c.parent.name || 'its constraint protocols defined in opts.where.'
|
||||
}`)
|
||||
}
|
||||
})
|
||||
this._methodNames.forEach(name => {
|
||||
defineMethod(this, name, target, types, impls)
|
||||
})
|
||||
}
|
||||
|
||||
hasImpl (arg, args) {
|
||||
args = args || []
|
||||
const fns = this._methodNames
|
||||
var gf
|
||||
if (typeof arg === 'function' && !arg.isGenfun) {
|
||||
arg = arg.prototype
|
||||
}
|
||||
args = args.map(arg => {
|
||||
if (typeof arg === 'function' && !arg.isGenfun) {
|
||||
return arg.prototype
|
||||
} else {
|
||||
return arg
|
||||
}
|
||||
})
|
||||
for (var i = 0; i < fns.length; i++) {
|
||||
gf = arg[fns[i]]
|
||||
if (!gf ||
|
||||
(gf.hasMethod
|
||||
? !gf.hasMethod.apply(gf, args)
|
||||
: typeof gf === 'function')) {
|
||||
return false
|
||||
}
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
// MyDuck.matches('a', ['this', 'c'])
|
||||
matches (thisType, argTypes) {
|
||||
if (!argTypes && isArray(thisType)) {
|
||||
argTypes = thisType
|
||||
thisType = 'this'
|
||||
}
|
||||
if (!thisType) {
|
||||
thisType = 'this'
|
||||
}
|
||||
if (!argTypes) {
|
||||
argTypes = []
|
||||
}
|
||||
return new Constraint(this, thisType, argTypes)
|
||||
}
|
||||
}
|
||||
Duck.prototype.isDuck = true
|
||||
Duck.prototype.isProtocol = true
|
||||
|
||||
const Protoduck = module.exports = define(['duck'], {
|
||||
createGenfun: ['duck', _metaCreateGenfun],
|
||||
addMethod: ['duck', _metaAddMethod]
|
||||
}, { name: 'Protoduck' })
|
||||
|
||||
const noImplFound = module.exports.noImplFound = genfun.noApplicableMethod
|
||||
|
||||
module.exports.define = define
|
||||
function define (types, spec, opts) {
|
||||
if (!isArray(types)) {
|
||||
// protocol(spec, opts?) syntax for method-based protocols
|
||||
opts = spec
|
||||
spec = types
|
||||
types = []
|
||||
}
|
||||
const duck = function (thisType, argTypes) {
|
||||
return duck.matches(thisType, argTypes)
|
||||
}
|
||||
Object.setPrototypeOf(duck, Duck.prototype)
|
||||
duck.isDerivable = true
|
||||
Object.defineProperty(duck, 'name', {
|
||||
value: (opts && opts.name) || 'Protocol'
|
||||
})
|
||||
if (opts && opts.where) {
|
||||
let where = opts.where
|
||||
if (!isArray(opts.where)) { where = [opts.where] }
|
||||
duck._constraints = where.map(w => w.isProtocol // `where: [Foo]`
|
||||
? w.matches()
|
||||
: w
|
||||
)
|
||||
} else {
|
||||
duck._constraints = []
|
||||
}
|
||||
duck.isProtocol = true
|
||||
duck._metaobject = opts && opts.metaobject
|
||||
duck._types = types
|
||||
duck._defaultImpls = {}
|
||||
duck._gfTypes = {}
|
||||
duck._methodNames = Object.keys(spec)
|
||||
duck._methodNames.forEach(name => {
|
||||
checkMethodSpec(duck, name, spec)
|
||||
})
|
||||
duck._constraints.forEach(c => c.attach(duck))
|
||||
return duck
|
||||
}
|
||||
|
||||
function checkMethodSpec (duck, name, spec) {
|
||||
let gfTypes = spec[name]
|
||||
if (typeof gfTypes === 'function') {
|
||||
duck._defaultImpls[name] = gfTypes
|
||||
gfTypes = [gfTypes]
|
||||
} if (typeof gfTypes[gfTypes.length - 1] === 'function') {
|
||||
duck._defaultImpls[name] = gfTypes.pop()
|
||||
} else {
|
||||
duck.isDerivable = false
|
||||
}
|
||||
duck._gfTypes[name] = gfTypes.map(typeId => {
|
||||
const idx = duck._types.indexOf(typeId)
|
||||
if (idx === -1) {
|
||||
throw new Error(
|
||||
`type '${
|
||||
typeId
|
||||
}' for function '${
|
||||
name
|
||||
}' does not match any protocol types (${
|
||||
duck._types.join(', ')
|
||||
}).`
|
||||
)
|
||||
} else {
|
||||
return idx
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
function defineMethod (duck, name, target, types, impls) {
|
||||
const methodTypes = duck._gfTypes[name].map(function (typeIdx) {
|
||||
return types[typeIdx]
|
||||
})
|
||||
for (let i = methodTypes.length - 1; i >= 0; i--) {
|
||||
if (methodTypes[i] === undefined) {
|
||||
methodTypes.pop()
|
||||
} else {
|
||||
break
|
||||
}
|
||||
}
|
||||
const useMetaobject = duck._metaobject && duck._metaobject !== Protoduck
|
||||
// `target` does not necessarily inherit from `Object`
|
||||
if (!Object.prototype.hasOwnProperty.call(target, name)) {
|
||||
// Make a genfun if there's nothing there
|
||||
const gf = useMetaobject
|
||||
? duck._metaobject.createGenfun(duck, target, name, null)
|
||||
: _metaCreateGenfun(duck, target, name, null)
|
||||
target[name] = gf
|
||||
} else if (typeof target[name] === 'function' && !target[name].isGenfun) {
|
||||
// Turn non-gf functions into genfuns
|
||||
const gf = useMetaobject
|
||||
? duck._metaobject.createGenfun(duck, target, name, target[name])
|
||||
: _metaCreateGenfun(duck, target, name, target[name])
|
||||
target[name] = gf
|
||||
}
|
||||
|
||||
const fn = impls[name] || duck._defaultImpls[name]
|
||||
if (fn) { // checkImpls made sure this is safe
|
||||
useMetaobject
|
||||
? duck._metaobject.addMethod(duck, target, name, methodTypes, fn)
|
||||
: _metaAddMethod(duck, target, name, methodTypes, fn)
|
||||
}
|
||||
}
|
||||
|
||||
function checkImpls (duck, target, impls) {
|
||||
duck._methodNames.forEach(function (name) {
|
||||
if (
|
||||
!impls[name] &&
|
||||
!duck._defaultImpls[name] &&
|
||||
// Existing methods on the target are acceptable defaults.
|
||||
typeof target[name] !== 'function'
|
||||
) {
|
||||
throw new Error(`Missing implementation for ${
|
||||
formatMethod(duck, name, duck.name)
|
||||
}. Make sure the method is present in your ${
|
||||
duck.name || 'protocol'
|
||||
} definition. Required methods: ${
|
||||
duck._methodNames.filter(m => {
|
||||
return !duck._defaultImpls[m]
|
||||
}).map(m => formatMethod(duck, m)).join(', ')
|
||||
}.`)
|
||||
}
|
||||
})
|
||||
Object.keys(impls).forEach(function (name) {
|
||||
if (duck._methodNames.indexOf(name) === -1) {
|
||||
throw new Error(
|
||||
`${name}() was included in the impl, but is not part of ${
|
||||
duck.name || 'the protocol'
|
||||
}. Allowed methods: ${
|
||||
duck._methodNames.map(m => formatMethod(duck, m)).join(', ')
|
||||
}.`
|
||||
)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
function formatMethod (duck, name, withDuckName) {
|
||||
return `${
|
||||
withDuckName && duck.name ? `${duck.name}#` : ''
|
||||
}${name}(${duck._gfTypes[name].map(n => duck._types[n]).join(', ')})`
|
||||
}
|
||||
|
||||
function checkArgTypes (duck, types) {
|
||||
var requiredTypes = duck._types
|
||||
if (types.length > requiredTypes.length) {
|
||||
throw new Error(
|
||||
`${
|
||||
duck.name || 'Protocol'
|
||||
} expects to be defined across ${
|
||||
requiredTypes.length
|
||||
} type${requiredTypes.length > 1 ? 's' : ''}, but ${
|
||||
types.length
|
||||
} ${types.length > 1 ? 'were' : 'was'} specified.`
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
function typeName (obj) {
|
||||
return (/\[object ([a-zA-Z0-9]+)\]/).exec(({}).toString.call(obj))[1]
|
||||
}
|
||||
|
||||
function installMethodErrorMessage (proto, gf, target, name) {
|
||||
noImplFound.add([gf], function (gf, thisArg, args) {
|
||||
let parent = Object.getPrototypeOf(thisArg)
|
||||
while (parent && parent[name] === gf) {
|
||||
parent = Object.getPrototypeOf(parent)
|
||||
}
|
||||
if (parent && parent[name] && typeof parent[name] === 'function') {
|
||||
}
|
||||
var msg = `No ${typeName(thisArg)} impl for ${
|
||||
proto.name ? `${proto.name}#` : ''
|
||||
}${name}(${[].map.call(args, typeName).join(', ')}). You must implement ${
|
||||
proto.name
|
||||
? formatMethod(proto, name, true)
|
||||
: `the protocol ${formatMethod(proto, name)} belongs to`
|
||||
} in order to call ${typeName(thisArg)}#${name}(${
|
||||
[].map.call(args, typeName).join(', ')
|
||||
}).`
|
||||
const err = new Error(msg)
|
||||
err.protocol = proto
|
||||
err.function = gf
|
||||
err.thisArg = thisArg
|
||||
err.args = args
|
||||
err.code = 'ENOIMPL'
|
||||
throw err
|
||||
})
|
||||
}
|
||||
|
||||
function isArray (x) {
|
||||
return Object.prototype.toString.call(x) === '[object Array]'
|
||||
}
|
||||
|
||||
// Metaobject Protocol
|
||||
Protoduck.impl(Protoduck) // defaults configured by definition
|
||||
|
||||
function _metaCreateGenfun (proto, target, name, deflt) {
|
||||
var gf = genfun({
|
||||
default: deflt,
|
||||
name: `${proto.name ? `${proto.name}#` : ''}${name}`
|
||||
})
|
||||
installMethodErrorMessage(proto, gf, target, name)
|
||||
gf.duck = proto
|
||||
return gf
|
||||
}
|
||||
|
||||
function _metaAddMethod (duck, target, name, methodTypes, fn) {
|
||||
return target[name].add(methodTypes, fn)
|
||||
}
|
||||
|
||||
// Constraints
|
||||
class Constraint {
|
||||
constructor (parent, thisType, argTypes) {
|
||||
this.parent = parent
|
||||
this.target = thisType
|
||||
this.types = argTypes
|
||||
}
|
||||
|
||||
attach (obj) {
|
||||
this.child = obj
|
||||
if (this.target === 'this') {
|
||||
this.thisIdx = 'this'
|
||||
} else {
|
||||
const idx = this.child._types.indexOf(this.target)
|
||||
if (idx === -1) {
|
||||
this.thisIdx = null
|
||||
} else {
|
||||
this.thisIdx = idx
|
||||
}
|
||||
}
|
||||
this.indices = this.types.map(typeId => {
|
||||
if (typeId === 'this') {
|
||||
return 'this'
|
||||
} else {
|
||||
const idx = this.child._types.indexOf(typeId)
|
||||
if (idx === -1) {
|
||||
return null
|
||||
} else {
|
||||
return idx
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
verify (target, types) {
|
||||
const thisType = (
|
||||
this.thisIdx === 'this' || this.thisIdx == null
|
||||
)
|
||||
? target
|
||||
: types[this.thisIdx]
|
||||
const parentTypes = this.indices.map(idx => {
|
||||
if (idx === 'this') {
|
||||
return target
|
||||
} else if (idx === 'this') {
|
||||
return types[this.thisIdx]
|
||||
} else if (idx === null) {
|
||||
return Object
|
||||
} else {
|
||||
return types[idx] || Object.prototype
|
||||
}
|
||||
})
|
||||
return this.parent.hasImpl(thisType, parentTypes)
|
||||
}
|
||||
}
|
||||
Constraint.prototype.isConstraint = true
|
88
node_modules/protoduck/package.json
generated
vendored
Normal file
88
node_modules/protoduck/package.json
generated
vendored
Normal file
|
@ -0,0 +1,88 @@
|
|||
{
|
||||
"_from": "protoduck@^5.0.1",
|
||||
"_id": "protoduck@5.0.1",
|
||||
"_inBundle": false,
|
||||
"_integrity": "sha512-WxoCeDCoCBY55BMvj4cAEjdVUFGRWed9ZxPlqTKYyw1nDDTQ4pqmnIMAGfJlg7Dx35uB/M+PHJPTmGOvaCaPTg==",
|
||||
"_location": "/protoduck",
|
||||
"_phantomChildren": {},
|
||||
"_requested": {
|
||||
"type": "range",
|
||||
"registry": true,
|
||||
"raw": "protoduck@^5.0.1",
|
||||
"name": "protoduck",
|
||||
"escapedName": "protoduck",
|
||||
"rawSpec": "^5.0.1",
|
||||
"saveSpec": null,
|
||||
"fetchSpec": "^5.0.1"
|
||||
},
|
||||
"_requiredBy": [
|
||||
"/pacote"
|
||||
],
|
||||
"_resolved": "https://registry.npmjs.org/protoduck/-/protoduck-5.0.1.tgz",
|
||||
"_shasum": "03c3659ca18007b69a50fd82a7ebcc516261151f",
|
||||
"_spec": "protoduck@^5.0.1",
|
||||
"_where": "/home/shimataro/projects/actions/ssh-key-action/node_modules/pacote",
|
||||
"author": {
|
||||
"name": "Kat Marchán",
|
||||
"email": "kzm@sykosomatic.org"
|
||||
},
|
||||
"bugs": {
|
||||
"url": "https://github.com/zkat/protoduck/issues"
|
||||
},
|
||||
"bundleDependencies": false,
|
||||
"dependencies": {
|
||||
"genfun": "^5.0.0"
|
||||
},
|
||||
"deprecated": false,
|
||||
"description": "Fancy duck typing for the most serious of ducks.",
|
||||
"devDependencies": {
|
||||
"mocha": "^5.2.0",
|
||||
"nyc": "^13.1.0",
|
||||
"standard": "^12.0.1",
|
||||
"standard-version": "^4.0.0",
|
||||
"tap": "^12.0.1",
|
||||
"weallbehave": "^1.0.3",
|
||||
"weallcontribute": "^1.0.8"
|
||||
},
|
||||
"files": [
|
||||
"index.js"
|
||||
],
|
||||
"homepage": "https://github.com/zkat/protoduck#readme",
|
||||
"keywords": [
|
||||
"oop",
|
||||
"util",
|
||||
"object oriented",
|
||||
"duck type",
|
||||
"ducktype",
|
||||
"ducktyping",
|
||||
"protocols",
|
||||
"multimethod",
|
||||
"clojure",
|
||||
"haskell",
|
||||
"rust",
|
||||
"generic",
|
||||
"functions",
|
||||
"clos",
|
||||
"polymorphism",
|
||||
"impl",
|
||||
"typeclass",
|
||||
"traits"
|
||||
],
|
||||
"license": "MIT",
|
||||
"main": "index.js",
|
||||
"name": "protoduck",
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git+https://github.com/zkat/protoduck.git"
|
||||
},
|
||||
"scripts": {
|
||||
"postrelease": "npm publish && git push --follow-tags",
|
||||
"prerelease": "npm t",
|
||||
"pretest": "standard",
|
||||
"release": "standard-version -s",
|
||||
"test": "tap -J --coverage test/*.js",
|
||||
"update-coc": "weallbehave -o . && git add CODE_OF_CONDUCT.md && git commit -m 'docs(coc): updated CODE_OF_CONDUCT.md'",
|
||||
"update-contrib": "weallcontribute -o . && git add CONTRIBUTING.md && git commit -m 'docs(contributing): updated CONTRIBUTING.md'"
|
||||
},
|
||||
"version": "5.0.1"
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue