66} = require ( '../annotations' ) ;
77const pipeParseResult = require ( '../../pipeParseResult' ) ;
88const {
9- isString, hasKey, hasValue , getValue,
9+ isString, hasKey, getValue,
1010} = require ( '../../predicates' ) ;
1111const parseObject = require ( '../parseObject' ) ;
1212const parseArray = require ( '../parseArray' ) ;
@@ -66,10 +66,32 @@ function constructArrayStructure(namespace, schema) {
6666 return element ;
6767}
6868
69+ function constructStructure ( namespace , schema , type ) {
70+ let element ;
71+
72+ if ( type === 'object' ) {
73+ element = constructObjectStructure ( namespace , schema ) ;
74+ } else if ( type === 'array' ) {
75+ element = constructArrayStructure ( namespace , schema ) ;
76+ } else if ( type === 'string' ) {
77+ element = new namespace . elements . String ( ) ;
78+ } else if ( type === 'number' || type === 'integer' ) {
79+ element = new namespace . elements . Number ( ) ;
80+ } else if ( type === 'boolean' ) {
81+ element = new namespace . elements . Boolean ( ) ;
82+ } else if ( type === 'null' ) {
83+ element = new namespace . elements . Null ( ) ;
84+ } else {
85+ throw new Error ( `Internal Inconsistency: constructStructure called with unexpected type: '${ type } '` ) ;
86+ }
87+
88+ return element ;
89+ }
90+
6991const openapi30Types = [ 'boolean' , 'object' , 'array' , 'number' , 'string' , 'integer' ] ;
7092const openapi31Types = openapi30Types . concat ( [ 'null' ] ) ;
71- const isValidOpenAPI30Type = R . anyPass ( R . map ( hasValue , openapi30Types ) ) ;
72- const isValidOpenAPI31Type = R . anyPass ( R . map ( hasValue , openapi31Types ) ) ;
93+ const isValidOpenAPI30Type = R . anyPass ( R . map ( R . equals , openapi30Types ) ) ;
94+ const isValidOpenAPI31Type = R . anyPass ( R . map ( R . equals , openapi31Types ) ) ;
7395
7496const typeToElementNameMap = {
7597 array : 'array' ,
@@ -81,6 +103,10 @@ const typeToElementNameMap = {
81103 string : 'string' ,
82104} ;
83105
106+ /*
107+ * Parse StringElement containing OpenAPI Schema type
108+ * Normalises result into an ArrayElement of StringElement
109+ */
84110function parseType ( context ) {
85111 let types ;
86112 let isValidType ;
@@ -94,16 +120,14 @@ function parseType(context) {
94120 }
95121
96122 const ensureValidType = R . unless (
97- isValidType ,
98- R . compose (
99- createWarning ( context . namespace , `'${ name } ' 'type' must be either ${ types . join ( ', ' ) } ` ) ,
100- getValue
101- )
123+ element => isValidType ( element . toValue ( ) ) ,
124+ createWarning ( context . namespace , `'${ name } ' 'type' must be either ${ types . join ( ', ' ) } ` )
102125 ) ;
103126
104127 return pipeParseResult ( context . namespace ,
105- parseString ( context , name , false ) ,
106- ensureValidType ) ;
128+ R . unless ( isString , value => createWarning ( context . namespace , `'${ name } ' 'type' is not a string` , value ) ) ,
129+ ensureValidType ,
130+ type => new context . namespace . elements . Array ( [ type ] ) ) ;
107131}
108132
109133// Returns whether the given element value matches the provided schema type
@@ -215,7 +239,7 @@ function parseSchema(context) {
215239 } ) ;
216240
217241 const parseMember = R . cond ( [
218- [ hasKey ( 'type' ) , parseType ( context ) ] ,
242+ [ hasKey ( 'type' ) , R . compose ( parseType ( context ) , getValue ) ] ,
219243 [ hasKey ( 'enum' ) , R . compose ( parseEnum ( context , name ) , getValue ) ] ,
220244 [ hasKey ( 'properties' ) , R . compose ( parseProperties , getValue ) ] ,
221245 [ hasKey ( 'items' ) , R . compose ( parseSubSchema , getValue ) ] ,
@@ -242,24 +266,16 @@ function parseSchema(context) {
242266
243267 const oneOf = schema . get ( 'oneOf' ) ;
244268 const enumerations = schema . get ( 'enum' ) ;
245- const type = schema . getValue ( 'type' ) ;
269+ const type = schema . getValue ( 'type' ) || [ ] ;
246270
247271 if ( oneOf ) {
248272 element = oneOf ;
249273 } else if ( enumerations ) {
250274 element = enumerations ;
251- } else if ( type === 'object' ) {
252- element = constructObjectStructure ( namespace , schema ) ;
253- } else if ( type === 'array' ) {
254- element = constructArrayStructure ( namespace , schema ) ;
255- } else if ( type === 'string' ) {
256- element = new namespace . elements . String ( ) ;
257- } else if ( type === 'number' || type === 'integer' ) {
258- element = new namespace . elements . Number ( ) ;
259- } else if ( type === 'boolean' ) {
260- element = new namespace . elements . Boolean ( ) ;
261- } else if ( type === 'null' ) {
262- element = new namespace . elements . Null ( ) ;
275+ } else if ( type . length > 1 ) {
276+ throw new Error ( 'Implementation error: unexpected multiple types' ) ;
277+ } else if ( type . length === 1 ) {
278+ element = constructStructure ( namespace , schema , type [ 0 ] ) ;
263279 } else {
264280 element = new namespace . elements . Enum ( ) ;
265281 element . enumerations = [
0 commit comments