initial commit

This commit is contained in:
Kevin Franklin Kim
2023-03-13 11:42:07 +01:00
commit 914626bfaf
23 changed files with 18372 additions and 0 deletions
+15
View File
@@ -0,0 +1,15 @@
{
"presets": [
"@babel/typescript",
[
"@babel/preset-env",
{
"targets": { "browsers": "defaults, not ie 11", "node": true },
"modules": false,
"useBuiltIns": false,
"loose": true
}
]
],
"plugins": ["@babel/plugin-transform-modules-commonjs"]
}
+12
View File
@@ -0,0 +1,12 @@
root = true
[*]
charset = utf-8
end_of_line = lf
indent_size = 2
indent_style = tab
insert_final_newline = true
trim_trailing_whitespace = true
[*.{yaml,yml}]
indent_style = space
+33
View File
@@ -0,0 +1,33 @@
{
"extends": [
"plugin:@typescript-eslint/eslint-recommended",
"plugin:prettier/recommended"
],
"plugins": [
"@typescript-eslint",
"prettier",
"prettier/@typescript-eslint"
],
"parser": "@typescript-eslint/parser",
"parserOptions": {
"sourceType": "module",
"ecmaVersion": 2020,
"ecmaFeatures": {
"jsx": true
}
},
"env": {
"es6": true,
"node": true,
"mocha": true,
"browser": true
},
"settings": {
"import/extensions": [
".js",
".ts"
]
},
"rules": {
}
}
+7
View File
@@ -0,0 +1,7 @@
version: 2
updates:
- package-ecosystem: npm
directory: '/'
open-pull-requests-limit: 20
schedule:
interval: weekly
+32
View File
@@ -0,0 +1,32 @@
name: Pull Requests
on:
# Triggers the workflow on push or pull request events but only for the main branch
push:
branches: [ main ]
pull_request:
branches: [ main ]
# Allows you to run this workflow manually from the Actions tab
workflow_dispatch:
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
env:
CI: true
jobs:
pull-request:
runs-on: ubuntu-latest
strategy:
matrix:
node-version: [16.x, 18.x]
steps:
- uses: actions/checkout@v3
- uses: actions/setup-node@v2
with:
node-version: ${{ matrix.node-version }}
- run: npm install
- run: npm run lint
- run: npm test
+12
View File
@@ -0,0 +1,12 @@
*.
.*
!.github/
!.babelrc
!.eslintrc
!.gitignore
!.editorconfig
!.prettierignore
!.prettierrc
dist/
node_modules/
tmp/
+2
View File
@@ -0,0 +1,2 @@
dist/
node_modules/
+5
View File
@@ -0,0 +1,5 @@
{
"singleQuote": true,
"semi": false,
"trailingComma": "es5"
}
+21
View File
@@ -0,0 +1,21 @@
The MIT License (MIT)
Copyright (c) 2023 bestbytes
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.
+1
View File
@@ -0,0 +1 @@
# Superstruct Fender
+17895
View File
File diff suppressed because it is too large Load Diff
+102
View File
@@ -0,0 +1,102 @@
{
"name": "superstruct-fender",
"description": "Superstruct extension with fender rules",
"version": "0.1.0",
"license": "MIT",
"type": "module",
"main": "./dist/index.cjs",
"module": "./dist/index.mjs",
"types": "./dist/index.d.ts",
"sideEffects": false,
"engines": {
"node": ">=16.0.0"
},
"repository": {
"type": "git",
"url": "git://github.com/foomo/superstruct-fender.git"
},
"publishConfig": {
"registry": "https://registry.npmjs.org"
},
"files": [
"dist"
],
"scripts": {
"build": "rm -rf ./{dist} && rollup --config ./rollup.config.js",
"clean": "rm -rf ./{dist,node_modules}",
"fix": "npm run fix:eslint && npm run fix:prettier",
"fix:eslint": "npm run lint:eslint --fix",
"fix:prettier": "npm run lint:prettier --write",
"lint": "npm run lint:eslint && npm run lint:prettier",
"lint:eslint": "eslint '{src,test}/*.{js,ts}'",
"lint:prettier": "prettier --list-different '**/*.{js,json,ts}'",
"release": "npm run build && npm run lint && np",
"test": "npm run build && npm run test:types && npm run test:mocha",
"test:mocha": "mocha --require ./test/register.cjs --require source-map-support/register ./test/index.ts",
"test:types": "tsc --noEmit && tsc --project ./test/tsconfig.json --noEmit",
"watch": "npm run build -- --watch"
},
"peerDependencies": {
"superstruct": "1.0.3"
},
"devDependencies": {
"@babel/cli": "7.21.0",
"@babel/core": "7.21.0",
"@babel/plugin-transform-modules-commonjs": "7.21.2",
"@babel/preset-env": "7.20.2",
"@babel/preset-typescript": "7.21.0",
"@babel/register": "7.21.0",
"@rollup/plugin-typescript": "11.0.0",
"@types/expect": "24.3.0",
"@types/lodash": "4.14.191",
"@types/mocha": "10.0.1",
"@types/node": "18.15.1",
"@typescript-eslint/eslint-plugin": "5.54.1",
"@typescript-eslint/parser": "5.54.1",
"babel-eslint": "10.1.0",
"eslint": "8.36.0",
"eslint-config-prettier": "8.7.0",
"eslint-plugin-import": "2.27.5",
"eslint-plugin-prettier": "4.2.1",
"is-email": "1.0.2",
"is-url": "1.2.4",
"is-uuid": "1.0.2",
"lodash": "4.17.21",
"mocha": "10.2.0",
"np": "7.6.3",
"prettier": "2.8.4",
"rollup": "3.19.1",
"typescript": "4.9.5"
},
"keywords": [
"api",
"array",
"assert",
"cast",
"check",
"checker",
"collection",
"data",
"error",
"express",
"hapi",
"interface",
"invalid",
"joi",
"json",
"list",
"model",
"object",
"orm",
"scalar",
"schema",
"struct",
"throw",
"type",
"types",
"valid",
"validate",
"validation",
"validator"
]
}
+20
View File
@@ -0,0 +1,20 @@
import { defineConfig } from 'rollup'
import typescript from '@rollup/plugin-typescript'
export default defineConfig({
input: './src/index.ts',
plugins: [typescript()],
output: [
{
file: './dist/index.mjs',
format: 'esm',
sourcemap: true,
},
{
file: './dist/index.cjs',
format: 'umd',
name: 'Superstruct Fender',
sourcemap: true,
},
],
})
+1
View File
@@ -0,0 +1 @@
export * from './structs/string'
+49
View File
@@ -0,0 +1,49 @@
import {Struct, refine} from "superstruct";
export function prefix<T extends string, S extends any>(
struct: Struct<T, S>,
expected: string
): Struct<T, S> {
return refine(struct, 'prefix', (value) => {
return (
value.startsWith(expected) ||
`Expected a ${struct.type} prefix \`${expected}\` but received "${value}"`
)
})
}
export function noPrefix<T extends string, S extends any>(
struct: Struct<T, S>,
expected: string
): Struct<T, S> {
return refine(struct, 'prefix', (value) => {
return (
!value.startsWith(expected) ||
`Expected a ${struct.type} no prefix \`${expected}\` but received "${value}"`
)
})
}
export function suffix<T extends string, S extends any>(
struct: Struct<T, S>,
expected: string
): Struct<T, S> {
return refine(struct, 'suffix', (value) => {
return (
value.endsWith(expected) ||
`Expected a ${struct.type} suffix \`${expected}\` but received "${value}"`
)
})
}
export function noSuffix<T extends string, S extends any>(
struct: Struct<T, S>,
expected: string
): Struct<T, S> {
return refine(struct, 'suffix', (value) => {
return (
!value.endsWith(expected) ||
`Expected a ${struct.type} no suffix \`${expected}\` but received "${value}"`
)
})
}
+93
View File
@@ -0,0 +1,93 @@
import assert, { CallTracker } from 'assert'
import fs from 'fs'
import { pick } from 'lodash'
import { basename, extname, resolve } from 'path'
import {
any,
assert as assertValue,
// eslint-disable-next-line import/named
Context,
create as createValue,
deprecated,
StructError,
} from 'superstruct'
describe('superstruct-fender', () => {
describe('validation', () => {
const kindsDir = resolve(__dirname, 'validation')
const kinds = fs
.readdirSync(kindsDir)
.filter((t) => t[0] !== '.')
.map((t) => basename(t, extname(t)))
for (const kind of kinds) {
describe(kind, () => {
const testsDir = resolve(kindsDir, kind)
const tests = fs
.readdirSync(testsDir)
.filter((t) => t[0] !== '.')
.map((t) => basename(t, extname(t)))
for (const name of tests) {
const module = require(resolve(testsDir, name))
const { Struct, data, create, only, skip, output, failures } = module
const run = only ? it.only : skip ? it.skip : it
run(name, () => {
let actual
let err
try {
if (create) {
actual = createValue(data, Struct)
} else {
assertValue(data, Struct)
actual = data
}
} catch (e) {
if (!(e instanceof StructError)) {
throw e
}
err = e
}
if ('output' in module) {
if (err) {
throw new Error(
`Expected "${name}" fixture not to throw an error but it did:\n\n${err}`
)
}
assert.deepStrictEqual(actual, output)
} else if ('failures' in module) {
if (!err) {
throw new Error(
`Expected "${name}" fixture to throw an error but it did not.`
)
}
const props = ['type', 'path', 'refinement', 'value', 'branch']
const actualFailures = err
.failures()
.map((failure) => pick(failure, ...props))
assert.deepStrictEqual(actualFailures, failures)
assert.deepStrictEqual(pick(err, ...props), failures[0])
} else {
throw new Error(
`The "${name}" fixture did not define an \`output\` or \`failures\` export.`
)
}
})
}
})
}
})
})
/**
* A helper for testing type signatures.
*/
export function test<T>(fn: (x: unknown) => T) {}
+3
View File
@@ -0,0 +1,3 @@
require('@babel/register')({
extensions: ['.js', '.jsx', '.ts', '.tsx'],
})
+4
View File
@@ -0,0 +1,4 @@
{
"extends": "../tsconfig.json",
"include": ["./**/*.ts"]
}
+16
View File
@@ -0,0 +1,16 @@
import {string} from 'superstruct'
import {prefix} from "../../../src/structs/string";
export const Struct = prefix(string(), "faa")
export const data = "foobar"
export const failures = [
{
value: 'foobar',
type: 'string',
refinement: 'prefix',
path: [],
branch: [data],
},
]
+8
View File
@@ -0,0 +1,8 @@
import {string} from 'superstruct'
import {suffix} from "../../../src/structs/string";
export const Struct = suffix(string(), "bar")
export const data = "foobar"
export const output = "foobar"
+16
View File
@@ -0,0 +1,16 @@
import {string} from 'superstruct'
import {suffix} from "../../../src/structs/string";
export const Struct = suffix(string(), "baz")
export const data = "foobar"
export const failures = [
{
value: 'foobar',
type: 'string',
refinement: 'suffix',
path: [],
branch: [data],
},
]
+8
View File
@@ -0,0 +1,8 @@
import {string} from 'superstruct'
import {prefix} from "../../../src/structs/string";
export const Struct = prefix(string(), "foo")
export const data = "foobar"
export const output = "foobar"
+17
View File
@@ -0,0 +1,17 @@
{
"include": ["./src/**/*.ts"],
"compilerOptions": {
"allowSyntheticDefaultImports": true,
"declaration": true,
"declarationMap": true,
"esModuleInterop": true,
"lib": ["esnext"],
"module": "esnext",
"moduleResolution": "node",
"outDir": "./dist",
"sourceMap": true,
"strict": true,
"suppressImplicitAnyIndexErrors": true,
"target": "es2020"
}
}