Skip to content

Commit

Permalink
Merge pull request #6 from upfrontIO/extensions
Browse files Browse the repository at this point in the history
Add properties to methods
  • Loading branch information
peyerluk authored Jul 5, 2018
2 parents fcc58ae + 145e931 commit 3dc6a13
Show file tree
Hide file tree
Showing 3 changed files with 183 additions and 5 deletions.
65 changes: 65 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,30 @@ output = {
}
```

Specifying a format:
```js
ms.string({format: 'email'})

output = {
type: 'string',
format: 'email'
}
```
Note: Check which formats are available with your JSON Schema
implementation before using this.


Specifying min and max length:
```js
ms.string({minLength: 3, maxLength: 50})

output = {
type: 'string',
minLength: 3,
maxLength: 50
}
```

Setting the required flag (only possible within an object):
```js
ms.obj({
Expand Down Expand Up @@ -180,6 +204,22 @@ output = {
}
```

Add title and description:
```js
ms.obj({
displayName: 'string',
}, {title: 'Title', description: 'Desc.'})
```

Add dependencies:
```js
ms.obj({
creditCard: 'string',
address: 'string'
}, {dependencies: {creditCard: 'address'}})
```


## Arrays

```js
Expand All @@ -191,6 +231,18 @@ output = {
}
```

You can use these additional modifiers:
```js
ms.arrayOf(ms.string(), {minItems: 1, maxItems: 3, uniqueItems: true})

output = {
type: 'array',
items: {type: 'string'},
minItems: 1,
maxItems: 3,
uniqueItems: true
}
```

## Enumerations

Expand All @@ -203,3 +255,16 @@ output = {
enum: ['foo', 'bar']
}
```

## Constant Value

```js
ms.const('foo')

// The output is the same as ms.enum('foo') as there is no equivalent
// to value in JSON schema.
output = {
type: 'string',
const: 'foo'
}
```
40 changes: 35 additions & 5 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -33,13 +33,16 @@ module.exports = {
// Methods
// -------

obj (microschema = {}, {strict, required} = {}) {
obj (microschema = {}, {strict, required, title, description, dependencies} = {}) {
const jsonSchema = {
type: 'object',
properties: {}
}

if (title) jsonSchema.title = title
if (description) jsonSchema.description = description
if (strict) jsonSchema.additionalProperties = false
if (dependencies) setDependencies(jsonSchema, dependencies)

if (required) {
if (!Array.isArray(required)) throw new Error("'required' must be an array")
Expand Down Expand Up @@ -87,22 +90,35 @@ module.exports = {
})
},


const (value) {
return this.decorate({
type: getJsonType(value),
const: value
})
},

// @param schemaOrType
// Pass in either a string or an object:
// 1. {String} A json schema type. E.g. 'string'
// Example: microschema.arrayOf('string')
// 2. {Object} JSON Schema
// Example: microschema.arrayOf({type: 'object', properties: {...}})
arrayOf (schemaOrType) {
arrayOf (schemaOrType, {minItems, maxItems, uniqueItems} = {}) {
const items = isString(schemaOrType) ? {type: schemaOrType} : schemaOrType

return this.decorate({
const s = this.decorate({
type: 'array',
items: items
})

if (minItems) s.minItems = minItems
if (maxItems) s.maxItems = maxItems
if (uniqueItems) s.uniqueItems = uniqueItems

return s
},

string ({pattern} = {}) {
string ({pattern, format, minLength, maxLength} = {}) {
const s = {type: 'string'}
if (pattern) {
if (pattern instanceof RegExp) {
Expand All @@ -114,6 +130,11 @@ module.exports = {
s.pattern = pattern
}
}

if (format) s.format = format
if (minLength) s.minLength = minLength
if (maxLength) s.maxLength = maxLength

return this.decorate(s)
},

Expand Down Expand Up @@ -178,3 +199,12 @@ function isString (str) {
function isNumber (nr) {
return typeof nr === 'number'
}

function setDependencies (jsonSchema, dependencies) {
const formattedDeps = {}
for (const prop in dependencies) {
const value = dependencies[prop]
formattedDeps[prop] = isString(value) ? [value] : value
}
jsonSchema.dependencies = formattedDeps
}
83 changes: 83 additions & 0 deletions test.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,44 @@ const ms = require('./index')
const test = require('ava').test
const assert = require('assert')

test('obj() creates an object with title and description', function (t) {
const schema = ms.obj({
displayName: 'string'
}, {
title: 'Title',
description: 'Desc.'
})

assert.deepEqual(schema, {
type: 'object',
properties: {
displayName: {type: 'string'}
},
title: 'Title',
description: 'Desc.'
})
})

test('obj() creates an object with dependencies', function (t) {
const schema = ms.obj({
name: 'string',
displayName: 'string'
}, {
dependencies: {name: 'displayName'}
})

assert.deepEqual(schema, {
type: 'object',
properties: {
name: {type: 'string'},
displayName: {type: 'string'}
},
dependencies: {
name: ['displayName']
}
})
})

test('strictObj() creates an object with a single property', function (t) {
const schema = ms.strictObj({foo: 'string'})

Expand Down Expand Up @@ -60,6 +98,14 @@ test('enum() creates an enum from an array', function (t) {
})
})

test('const() creates a const value', function (t) {
const schema = ms.const('foo')
assert.deepEqual(schema, {
type: 'string',
const: 'foo'
})
})


test('arrayOf() creates an array with a type of its items', function (t) {
const schema = ms.arrayOf('integer')
Expand All @@ -69,6 +115,23 @@ test('arrayOf() creates an array with a type of its items', function (t) {
})
})


test('arrayOf() creates an array with additional properties', function (t) {
const schema = ms.arrayOf(ms.string(), {
minItems: 1,
maxItems: 3,
uniqueItems: true
})

assert.deepEqual(schema, {
type: 'array',
items: {type: 'string'},
minItems: 1,
maxItems: 3,
uniqueItems: true
})
})

test('string() creates a type string', function (t) {
const schema = ms.string()
assert.deepEqual(schema, {type: 'string'})
Expand Down Expand Up @@ -124,6 +187,26 @@ test('string({pattern}) does not accept a javascript regex with flags', function
})
})


test('string({format}) adds a format', function (t) {
const schema = ms.string({format: 'email'})

assert.deepEqual(schema, {
type: 'string',
format: 'email'
})
})

test('string({minLength, maxLength}) adds these properties', function (t) {
const schema = ms.string({minLength: 3, maxLength: 50})

assert.deepEqual(schema, {
type: 'string',
minLength: 3,
maxLength: 50
})
})

test('number() creates a type number', function (t) {
const schema = ms.number()
assert.deepEqual(schema, {type: 'number'})
Expand Down

0 comments on commit 3dc6a13

Please sign in to comment.