document-validators.spec.js 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300
  1. import {expect} from 'chai';
  2. import {format} from '@e22m4u/js-format';
  3. import {OPENAPI_VERSION} from './constants.js';
  4. import {validateShallowOADocumentObject} from './document-validators.js';
  5. const MINIMAL_DOCUMENT = {
  6. openapi: OPENAPI_VERSION,
  7. info: {title: 'API Documentation', version: '0.0.1'},
  8. };
  9. describe('document validators', function () {
  10. describe('validateShallowOADocumentObject', function () {
  11. it('should require the first parameter to be an Object', function () {
  12. const throwable = v => () => validateShallowOADocumentObject(v);
  13. const error = s =>
  14. format(
  15. 'OpenAPI Document Object must be an Object, but %s was given.',
  16. s,
  17. );
  18. expect(throwable('str')).to.throw(error('"str"'));
  19. expect(throwable('')).to.throw(error('""'));
  20. expect(throwable(10)).to.throw(error('10'));
  21. expect(throwable(0)).to.throw(error('0'));
  22. expect(throwable(true)).to.throw(error('true'));
  23. expect(throwable(false)).to.throw(error('false'));
  24. expect(throwable([])).to.throw(error('Array'));
  25. expect(throwable(undefined)).to.throw(error('undefined'));
  26. expect(throwable(null)).to.throw(error('null'));
  27. throwable(MINIMAL_DOCUMENT)();
  28. });
  29. it('should require the "info" property to be an Object', function () {
  30. const throwable = v => () =>
  31. validateShallowOADocumentObject({
  32. openapi: OPENAPI_VERSION,
  33. info: v,
  34. });
  35. const error = s =>
  36. format('Property "info" must be an Object, but %s was given.', s);
  37. expect(throwable('str')).to.throw(error('"str"'));
  38. expect(throwable('')).to.throw(error('""'));
  39. expect(throwable(10)).to.throw(error('10'));
  40. expect(throwable(0)).to.throw(error('0'));
  41. expect(throwable(true)).to.throw(error('true'));
  42. expect(throwable(false)).to.throw(error('false'));
  43. expect(throwable([])).to.throw(error('Array'));
  44. expect(throwable(undefined)).to.throw(error('undefined'));
  45. expect(throwable(null)).to.throw(error('null'));
  46. throwable({title: 'API Documentation', version: '0.0.1'})();
  47. });
  48. it('should require the "info.title" property to be a non-empty String', function () {
  49. const throwable = v => () =>
  50. validateShallowOADocumentObject({
  51. openapi: OPENAPI_VERSION,
  52. info: {
  53. title: v,
  54. version: '0.0.1',
  55. },
  56. });
  57. const error = s =>
  58. format(
  59. 'Property "info.title" must be a non-empty String, but %s was given.',
  60. s,
  61. );
  62. expect(throwable('')).to.throw(error('""'));
  63. expect(throwable(10)).to.throw(error('10'));
  64. expect(throwable(0)).to.throw(error('0'));
  65. expect(throwable(true)).to.throw(error('true'));
  66. expect(throwable(false)).to.throw(error('false'));
  67. expect(throwable([])).to.throw(error('Array'));
  68. expect(throwable({})).to.throw(error('Object'));
  69. expect(throwable(undefined)).to.throw(error('undefined'));
  70. expect(throwable(null)).to.throw(error('null'));
  71. throwable('API Documentation')();
  72. });
  73. it('should require the "jsonSchemaDialect" property to be a non-empty String', function () {
  74. const throwable = v => () =>
  75. validateShallowOADocumentObject({
  76. ...MINIMAL_DOCUMENT,
  77. jsonSchemaDialect: v,
  78. });
  79. const error = s =>
  80. format(
  81. 'Property "jsonSchemaDialect" must be a non-empty String, but %s was given.',
  82. s,
  83. );
  84. expect(throwable('')).to.throw(error('""'));
  85. expect(throwable(10)).to.throw(error('10'));
  86. expect(throwable(0)).to.throw(error('0'));
  87. expect(throwable(true)).to.throw(error('true'));
  88. expect(throwable(false)).to.throw(error('false'));
  89. expect(throwable([])).to.throw(error('Array'));
  90. expect(throwable({})).to.throw(error('Object'));
  91. expect(throwable(null)).to.throw(error('null'));
  92. throwable('https://json-schema.org/draft/2020-12/schema')();
  93. throwable(undefined)();
  94. });
  95. it('should require the "servers" property to be an Array', function () {
  96. const throwable = v => () =>
  97. validateShallowOADocumentObject({
  98. ...MINIMAL_DOCUMENT,
  99. servers: v,
  100. });
  101. const error = s =>
  102. format('Property "servers" must be an Array, but %s was given.', s);
  103. expect(throwable('str')).to.throw(error('"str"'));
  104. expect(throwable('')).to.throw(error('""'));
  105. expect(throwable(10)).to.throw(error('10'));
  106. expect(throwable(0)).to.throw(error('0'));
  107. expect(throwable(true)).to.throw(error('true'));
  108. expect(throwable(false)).to.throw(error('false'));
  109. expect(throwable({})).to.throw(error('Object'));
  110. expect(throwable(null)).to.throw(error('null'));
  111. throwable([{url: 'http://localhost'}])();
  112. throwable([])();
  113. });
  114. it('should require elements of the "servers" property to be an Object', function () {
  115. const throwable = v => () =>
  116. validateShallowOADocumentObject({
  117. ...MINIMAL_DOCUMENT,
  118. servers: [v],
  119. });
  120. const error = s =>
  121. format('Element "servers[0]" must be an Object, but %s was given.', s);
  122. expect(throwable('str')).to.throw(error('"str"'));
  123. expect(throwable('')).to.throw(error('""'));
  124. expect(throwable(10)).to.throw(error('10'));
  125. expect(throwable(0)).to.throw(error('0'));
  126. expect(throwable(true)).to.throw(error('true'));
  127. expect(throwable(false)).to.throw(error('false'));
  128. expect(throwable([])).to.throw(error('Array'));
  129. expect(throwable(null)).to.throw(error('null'));
  130. throwable({url: 'http://localhost'})();
  131. });
  132. it('should require the "paths" property to be an Object', function () {
  133. const throwable = v => () =>
  134. validateShallowOADocumentObject({
  135. ...MINIMAL_DOCUMENT,
  136. paths: v,
  137. });
  138. const error = s =>
  139. format('Property "paths" must be an Object, but %s was given.', s);
  140. expect(throwable('str')).to.throw(error('"str"'));
  141. expect(throwable('')).to.throw(error('""'));
  142. expect(throwable(10)).to.throw(error('10'));
  143. expect(throwable(0)).to.throw(error('0'));
  144. expect(throwable(true)).to.throw(error('true'));
  145. expect(throwable(false)).to.throw(error('false'));
  146. expect(throwable([])).to.throw(error('Array'));
  147. expect(throwable(null)).to.throw(error('null'));
  148. throwable({})();
  149. });
  150. it('should require the "webhooks" property to be an Object', function () {
  151. const throwable = v => () =>
  152. validateShallowOADocumentObject({
  153. ...MINIMAL_DOCUMENT,
  154. webhooks: v,
  155. });
  156. const error = s =>
  157. format('Property "webhooks" must be an Object, but %s was given.', s);
  158. expect(throwable('str')).to.throw(error('"str"'));
  159. expect(throwable('')).to.throw(error('""'));
  160. expect(throwable(10)).to.throw(error('10'));
  161. expect(throwable(0)).to.throw(error('0'));
  162. expect(throwable(true)).to.throw(error('true'));
  163. expect(throwable(false)).to.throw(error('false'));
  164. expect(throwable([])).to.throw(error('Array'));
  165. expect(throwable(null)).to.throw(error('null'));
  166. throwable({})();
  167. });
  168. it('should require the "components" property to be an Object', function () {
  169. const throwable = v => () =>
  170. validateShallowOADocumentObject({
  171. ...MINIMAL_DOCUMENT,
  172. components: v,
  173. });
  174. const error = s =>
  175. format('Property "components" must be an Object, but %s was given.', s);
  176. expect(throwable('str')).to.throw(error('"str"'));
  177. expect(throwable('')).to.throw(error('""'));
  178. expect(throwable(10)).to.throw(error('10'));
  179. expect(throwable(0)).to.throw(error('0'));
  180. expect(throwable(true)).to.throw(error('true'));
  181. expect(throwable(false)).to.throw(error('false'));
  182. expect(throwable([])).to.throw(error('Array'));
  183. expect(throwable(null)).to.throw(error('null'));
  184. throwable({})();
  185. });
  186. it('should require the "security" property to be an Array', function () {
  187. const throwable = v => () =>
  188. validateShallowOADocumentObject({
  189. ...MINIMAL_DOCUMENT,
  190. security: v,
  191. });
  192. const error = s =>
  193. format('Property "security" must be an Array, but %s was given.', s);
  194. expect(throwable('str')).to.throw(error('"str"'));
  195. expect(throwable('')).to.throw(error('""'));
  196. expect(throwable(10)).to.throw(error('10'));
  197. expect(throwable(0)).to.throw(error('0'));
  198. expect(throwable(true)).to.throw(error('true'));
  199. expect(throwable(false)).to.throw(error('false'));
  200. expect(throwable({})).to.throw(error('Object'));
  201. expect(throwable(null)).to.throw(error('null'));
  202. throwable([{}])();
  203. throwable([])();
  204. });
  205. it('should require elements of the "security" property to be an Object', function () {
  206. const throwable = v => () =>
  207. validateShallowOADocumentObject({
  208. ...MINIMAL_DOCUMENT,
  209. security: [v],
  210. });
  211. const error = s =>
  212. format('Element "security[0]" must be an Object, but %s was given.', s);
  213. expect(throwable('str')).to.throw(error('"str"'));
  214. expect(throwable('')).to.throw(error('""'));
  215. expect(throwable(10)).to.throw(error('10'));
  216. expect(throwable(0)).to.throw(error('0'));
  217. expect(throwable(true)).to.throw(error('true'));
  218. expect(throwable(false)).to.throw(error('false'));
  219. expect(throwable([])).to.throw(error('Array'));
  220. expect(throwable(null)).to.throw(error('null'));
  221. throwable({apiKey: []})();
  222. throwable({})();
  223. });
  224. it('should require the "tags" property to be an Array', function () {
  225. const throwable = v => () =>
  226. validateShallowOADocumentObject({
  227. ...MINIMAL_DOCUMENT,
  228. tags: v,
  229. });
  230. const error = s =>
  231. format('Property "tags" must be an Array, but %s was given.', s);
  232. expect(throwable('str')).to.throw(error('"str"'));
  233. expect(throwable('')).to.throw(error('""'));
  234. expect(throwable(10)).to.throw(error('10'));
  235. expect(throwable(0)).to.throw(error('0'));
  236. expect(throwable(true)).to.throw(error('true'));
  237. expect(throwable(false)).to.throw(error('false'));
  238. expect(throwable({})).to.throw(error('Object'));
  239. expect(throwable(null)).to.throw(error('null'));
  240. throwable([{name: 'tag'}])();
  241. throwable([])();
  242. });
  243. it('should require elements of the "tags" property to be an Object', function () {
  244. const throwable = v => () =>
  245. validateShallowOADocumentObject({
  246. ...MINIMAL_DOCUMENT,
  247. tags: [v],
  248. });
  249. const error = s =>
  250. format('Element "tags[0]" must be an Object, but %s was given.', s);
  251. expect(throwable('str')).to.throw(error('"str"'));
  252. expect(throwable('')).to.throw(error('""'));
  253. expect(throwable(10)).to.throw(error('10'));
  254. expect(throwable(0)).to.throw(error('0'));
  255. expect(throwable(true)).to.throw(error('true'));
  256. expect(throwable(false)).to.throw(error('false'));
  257. expect(throwable([])).to.throw(error('Array'));
  258. expect(throwable(null)).to.throw(error('null'));
  259. throwable({name: 'tag'})();
  260. throwable({})();
  261. });
  262. it('should require the "externalDocs" property to be an Object', function () {
  263. const throwable = v => () =>
  264. validateShallowOADocumentObject({
  265. ...MINIMAL_DOCUMENT,
  266. externalDocs: v,
  267. });
  268. const error = s =>
  269. format(
  270. 'Property "externalDocs" must be an Object, but %s was given.',
  271. s,
  272. );
  273. expect(throwable('str')).to.throw(error('"str"'));
  274. expect(throwable('')).to.throw(error('""'));
  275. expect(throwable(10)).to.throw(error('10'));
  276. expect(throwable(0)).to.throw(error('0'));
  277. expect(throwable(true)).to.throw(error('true'));
  278. expect(throwable(false)).to.throw(error('false'));
  279. expect(throwable([])).to.throw(error('Array'));
  280. expect(throwable(null)).to.throw(error('null'));
  281. throwable({url: 'https://example.com'})();
  282. throwable(undefined)();
  283. });
  284. });
  285. });