Skip to content

Commit 6135f0e

Browse files
authored
Merge pull request #3 from VShingala/feat/pmH1bdTo509
Feat/pm h1bd to509
2 parents 884de68 + 8bfef94 commit 6135f0e

File tree

6 files changed

+111
-18
lines changed

6 files changed

+111
-18
lines changed

src/lib/core/run.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ function resolve(obj, data, values, property) {
8383
}
8484

8585
// TODO provide types?
86-
function run(refs, schema, container, synchronous) {
86+
function run(refs, schema, container, synchronous, validateSchema) {
8787
if (Object.prototype.toString.call(schema) !== '[object Object]') {
8888
throw new Error(`Invalid input, expecting object but given ${typeof schema}`);
8989
}
@@ -100,7 +100,7 @@ function run(refs, schema, container, synchronous) {
100100
refDepthMin,
101101
refDepthMax,
102102
});
103-
const result = traverse(utils.clone(schema), [], resolveSchema);
103+
const result = traverse(utils.clone(schema), [], resolveSchema, undefined, validateSchema);
104104

105105
if (optionAPI('resolveJsonPath')) {
106106
return {

src/lib/core/traverse.js

Lines changed: 37 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ function getMeta({ $comment: comment, title, description }) {
1515
}
1616

1717
// TODO provide types
18-
function traverse(schema, path, resolve, rootSchema) {
18+
function traverse(schema, path, resolve, rootSchema, validateSchema) {
1919
schema = resolve(schema, null, path);
2020

2121
if (schema && (schema.oneOf || schema.anyOf || schema.allOf)) {
@@ -36,14 +36,42 @@ function traverse(schema, path, resolve, rootSchema) {
3636
// example values have highest precedence
3737
if (optionAPI('useExamplesValue') && Array.isArray(schema.examples)) {
3838
// include `default` value as example too
39-
const fixedExamples = schema.examples
40-
.concat('default' in schema ? [schema.default] : []);
41-
42-
return { value: utils.typecast(null, schema, () => random.pick(fixedExamples)), context };
39+
const fixedExamples = schema.examples.concat(
40+
'default' in schema ? [schema.default] : []);
41+
const randomExample = random.pick(fixedExamples);
42+
if (validateSchema) {
43+
const result = validateSchema(schema, randomExample);
44+
// Use example only if valid
45+
if (result && result.length === 0) {
46+
return {
47+
value: utils.typecast(null, schema, () => randomExample),
48+
context,
49+
};
50+
}
51+
} else {
52+
console.warn('Taking example from schema without validation');
53+
return {
54+
value: utils.typecast(null, schema, () => randomExample),
55+
context,
56+
};
57+
}
4358
}
4459
// If schema contains single example property
4560
if (optionAPI('useExamplesValue') && schema.example) {
46-
return { value: utils.typecast(null, schema, () => schema.example), context };
61+
if (validateSchema) {
62+
const result = validateSchema(schema, schema.example);
63+
64+
// Use example only if valid
65+
if (result && result.length === 0) {
66+
return {
67+
value: utils.typecast(null, schema, () => schema.example),
68+
context,
69+
};
70+
}
71+
} else {
72+
console.warn('Taking example from schema without validation');
73+
return { value: utils.typecast(null, schema, () => schema.example), context };
74+
}
4775
}
4876

4977
if (optionAPI('useDefaultValue') && 'default' in schema) {
@@ -66,15 +94,15 @@ function traverse(schema, path, resolve, rootSchema) {
6694

6795
// build new object value from not-schema!
6896
if (schema.type && schema.type === 'object') {
69-
const { value, context: innerContext } = traverse(schema, path.concat(['not']), resolve, rootSchema);
97+
const { value, context: innerContext } = traverse(schema, path.concat(['not']), resolve, rootSchema, validateSchema);
7098
return { value: utils.clean(value, schema, false), context: { ...context, items: innerContext } };
7199
}
72100
}
73101

74102
// thunks can return sub-schemas
75103
if (typeof schema.thunk === 'function') {
76104
// result is already cleaned in thunk
77-
const { value, context: innerContext } = traverse(schema.thunk(rootSchema), path, resolve);
105+
const { value, context: innerContext } = traverse(schema.thunk(rootSchema), path, resolve, undefined, validateSchema);
78106
return { value, context: { ...context, items: innerContext } };
79107
}
80108

@@ -172,7 +200,7 @@ function traverse(schema, path, resolve, rootSchema) {
172200
Object.keys(schema).forEach(prop => {
173201
if (pruneProperties.includes(prop)) return;
174202
if (typeof schema[prop] === 'object' && prop !== 'definitions') {
175-
const { value, context: innerContext } = traverse(schema[prop], path.concat([prop]), resolve, valueCopy);
203+
const { value, context: innerContext } = traverse(schema[prop], path.concat([prop]), resolve, valueCopy, validateSchema);
176204
valueCopy[prop] = utils.clean(value, schema[prop], false);
177205
contextCopy[prop] = innerContext;
178206
} else {

src/lib/generators/coreFormat.js

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,10 @@
11
import random from '../core/random';
22

3+
/**
4+
* Added few formats from latest json-schema-faker. see below for source
5+
* https://github.com/json-schema-faker/json-schema-faker/blob/master/src/lib/generators/coreFormat.js
6+
*
7+
*/
38
const FRAGMENT = '[a-zA-Z][a-zA-Z0-9+-.]*';
49
const URI_PATTERN = `https?://{hostname}(?:${FRAGMENT})+`;
510
const PARAM_PATTERN = '(?:\\?([a-z]{1,7}(=\\w{1,5})?&){0,3})?';

src/lib/index.js

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -93,18 +93,18 @@ const jsf = (schema, refs, cwd) => {
9393
return jsf.generate(schema, refs);
9494
};
9595

96-
jsf.generateWithContext = (schema, refs) => {
96+
jsf.generateWithContext = (schema, refs, validateSchema) => {
9797
const $refs = getRefs(refs, schema);
9898

99-
return run($refs, schema, container, true);
99+
return run($refs, schema, container, true, validateSchema);
100100
};
101101

102-
jsf.generate = (schema, refs) => renderJS(
103-
jsf.generateWithContext(schema, refs),
102+
jsf.generate = (schema, refs, validateSchema) => renderJS(
103+
jsf.generateWithContext(schema, refs, validateSchema),
104104
);
105105

106-
jsf.generateYAML = (schema, refs) => renderYAML(
107-
jsf.generateWithContext(schema, refs),
106+
jsf.generateYAML = (schema, refs, validateSchema) => renderYAML(
107+
jsf.generateWithContext(schema, refs, validateSchema),
108108
);
109109

110110
jsf.resolveWithContext = (schema, refs, cwd) => {

src/lib/types/array.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ function unique(path, items, value, sample, resolve, traverseCallback) {
2424
items.forEach(walk);
2525

2626
// TODO: find a better solution?
27-
let limit = 100;
27+
let limit = 10;
2828

2929
while (tmp.length !== items.length) {
3030
if (!walk(traverseCallback(value.items || sample, path, resolve))) {

tests/unit/core/index.spec.js

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
import { expect } from 'chai';
2+
import jsf from '../../../src/lib';
3+
4+
describe('jsf generate', () => {
5+
it('Take example without validation', () => {
6+
const schema = {
7+
type: 'integer',
8+
format: 'int32',
9+
example: 123,
10+
};
11+
jsf.option('useExamplesValue', true);
12+
expect(jsf.generate(schema)).to.eql(123);
13+
});
14+
it('Take example with validation', () => {
15+
const schema = {
16+
type: 'integer',
17+
format: 'int32',
18+
example: 123,
19+
};
20+
jsf.option('useExamplesValue', true);
21+
expect(jsf.generate(schema, undefined, () => { return []; })).to.eql(123);
22+
});
23+
it('Generate fake data when example is not valid', () => {
24+
const schema = {
25+
type: 'integer',
26+
format: 'int32',
27+
example: '123',
28+
};
29+
jsf.option('useExamplesValue', true);
30+
expect(jsf.generate(schema, undefined, () => { return [{ error: 'some' }]; })).to.be.an('number');
31+
});
32+
it('Take one example from examples without validation', () => {
33+
const schema = {
34+
type: 'integer',
35+
format: 'int32',
36+
examples: [123, 456],
37+
};
38+
jsf.option('useExamplesValue', true);
39+
expect([123, 456]).to.include(jsf.generate(schema));
40+
});
41+
it('Take one example from examples with validation', () => {
42+
const schema = {
43+
type: 'integer',
44+
format: 'int32',
45+
examples: [123, 456],
46+
};
47+
jsf.option('useExamplesValue', true);
48+
expect([123, 456]).to.include(jsf.generate(schema, undefined, () => { return []; }));
49+
});
50+
it('Generate fake data when example from examples is not valid', () => {
51+
const schema = {
52+
type: 'integer',
53+
format: 'int32',
54+
examples: ['123', '456'],
55+
};
56+
jsf.option('useExamplesValue', true);
57+
expect(jsf.generate(schema, undefined, () => { return [{ error: 'some' }]; })).to.be.an('number');
58+
});
59+
});
60+

0 commit comments

Comments
 (0)