@stoplight/elements-core 9.0.12-beta-0.1 → 9.0.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (417) hide show
  1. package/{dist/components → components}/Docs/Docs.d.ts +1 -14
  2. package/{dist/components → components}/Docs/HttpOperation/Body.d.ts +1 -9
  3. package/{dist/components → components}/Docs/HttpOperation/HttpOperation.d.ts +2 -6
  4. package/{dist/components → components}/Docs/HttpOperation/Request.d.ts +0 -6
  5. package/{dist/components → components}/Docs/HttpOperation/Responses.d.ts +1 -12
  6. package/{dist/components → components}/TableOfContents/types.d.ts +7 -0
  7. package/{dist/index.esm.js → index.esm.js} +86 -525
  8. package/{dist/index.js → index.js} +86 -525
  9. package/{dist/index.mjs → index.mjs} +86 -525
  10. package/package.json +14 -74
  11. package/.storybook/main.js +0 -6
  12. package/.storybook/manager.js +0 -1
  13. package/.storybook/preview.jsx +0 -50
  14. package/dist/LICENSE +0 -190
  15. package/dist/README.md +0 -1
  16. package/dist/components/Docs/HttpOperation/LazySchemaTreePreviewer.d.ts +0 -34
  17. package/dist/package.json +0 -64
  18. package/jest.config.js +0 -10
  19. package/src/__fixtures__/articles/basic.md +0 -10
  20. package/src/__fixtures__/articles/kitchen-sink.md +0 -318
  21. package/src/__fixtures__/articles/long-page-heading.md +0 -955
  22. package/src/__fixtures__/articles/multiple-try-its.md +0 -54
  23. package/src/__fixtures__/articles/schema-with-refs.ts +0 -82
  24. package/src/__fixtures__/http-request.json +0 -11
  25. package/src/__fixtures__/models/model-with-no-examples.json +0 -15
  26. package/src/__fixtures__/models/model-with-one-example.json +0 -23
  27. package/src/__fixtures__/models/model-with-three-examples.json +0 -35
  28. package/src/__fixtures__/operations/application-octet-stream-post.ts +0 -39
  29. package/src/__fixtures__/operations/base64-file-upload.ts +0 -43
  30. package/src/__fixtures__/operations/big-response.ts +0 -4690
  31. package/src/__fixtures__/operations/bundled-parameter.ts +0 -128
  32. package/src/__fixtures__/operations/empty-response.ts +0 -15
  33. package/src/__fixtures__/operations/examples-request-body.ts +0 -135
  34. package/src/__fixtures__/operations/head-todos.ts +0 -49
  35. package/src/__fixtures__/operations/invalid-response-example.ts +0 -45
  36. package/src/__fixtures__/operations/multipart-formdata-post.ts +0 -61
  37. package/src/__fixtures__/operations/operation-minimal.ts +0 -11
  38. package/src/__fixtures__/operations/operation-parameters.ts +0 -337
  39. package/src/__fixtures__/operations/operation-with-examples.ts +0 -113
  40. package/src/__fixtures__/operations/operation-without-servers.ts +0 -16
  41. package/src/__fixtures__/operations/patch-todos.ts +0 -49
  42. package/src/__fixtures__/operations/put-todos.ts +0 -862
  43. package/src/__fixtures__/operations/referenced-body.ts +0 -62
  44. package/src/__fixtures__/operations/request-body-empty-schema.ts +0 -35
  45. package/src/__fixtures__/operations/request-body.ts +0 -62
  46. package/src/__fixtures__/operations/securedOperation.ts +0 -118
  47. package/src/__fixtures__/operations/security-basic.ts +0 -24
  48. package/src/__fixtures__/operations/security-bearer.ts +0 -25
  49. package/src/__fixtures__/operations/simple-get.ts +0 -17
  50. package/src/__fixtures__/operations/simple.ts +0 -103
  51. package/src/__fixtures__/operations/string-numeric-enums.ts +0 -32
  52. package/src/__fixtures__/operations/urlencoded-post-oneof.ts +0 -81
  53. package/src/__fixtures__/operations/urlencoded-post.ts +0 -54
  54. package/src/__fixtures__/operations/vendor-extensions.ts +0 -337
  55. package/src/__fixtures__/operations/with-url-variables.ts +0 -47
  56. package/src/__fixtures__/operations/x-code-samples.ts +0 -348
  57. package/src/__fixtures__/schemas/circular.ts +0 -1906
  58. package/src/__fixtures__/schemas/contact.json +0 -293
  59. package/src/__fixtures__/schemas/media-entry.json +0 -69
  60. package/src/__fixtures__/schemas/simple.json +0 -27
  61. package/src/__fixtures__/schemas/todo-full.v1.json +0 -35
  62. package/src/__fixtures__/schemas/todo-partial.v1.json +0 -14
  63. package/src/__fixtures__/schemas/user.v1.json +0 -17
  64. package/src/__fixtures__/security-schemes/index.ts +0 -38
  65. package/src/__fixtures__/services/petstore.ts +0 -167
  66. package/src/__fixtures__/services/with-unnamed-servers.ts +0 -38
  67. package/src/__fixtures__/services/with-url-variables.ts +0 -83
  68. package/src/__fixtures__/services/without-origin.ts +0 -20
  69. package/src/__fixtures__/table-of-contents/nested.ts +0 -44
  70. package/src/__fixtures__/table-of-contents/studio-template.ts +0 -100
  71. package/src/__fixtures__/table-of-contents/studio.ts +0 -559
  72. package/src/components/Docs/Article/Article.spec.tsx +0 -38
  73. package/src/components/Docs/Article/Article.stories.tsx +0 -17
  74. package/src/components/Docs/Article/index.tsx +0 -38
  75. package/src/components/Docs/Docs.stories.tsx +0 -33
  76. package/src/components/Docs/Docs.tsx +0 -272
  77. package/src/components/Docs/HttpOperation/Badges.tsx +0 -49
  78. package/src/components/Docs/HttpOperation/Body.tsx +0 -115
  79. package/src/components/Docs/HttpOperation/Callbacks.tsx +0 -89
  80. package/src/components/Docs/HttpOperation/HttpOperation.spec.tsx +0 -787
  81. package/src/components/Docs/HttpOperation/HttpOperation.stories.ts +0 -14
  82. package/src/components/Docs/HttpOperation/HttpOperation.tsx +0 -260
  83. package/src/components/Docs/HttpOperation/LazySchemaTreePreviewer.tsx +0 -651
  84. package/src/components/Docs/HttpOperation/Parameters.spec.tsx +0 -101
  85. package/src/components/Docs/HttpOperation/Parameters.tsx +0 -118
  86. package/src/components/Docs/HttpOperation/Request.tsx +0 -152
  87. package/src/components/Docs/HttpOperation/Responses.tsx +0 -301
  88. package/src/components/Docs/HttpOperation/index.ts +0 -1
  89. package/src/components/Docs/HttpService/AdditionalInfo.stories.ts +0 -48
  90. package/src/components/Docs/HttpService/AdditionalInfo.tsx +0 -61
  91. package/src/components/Docs/HttpService/ExportButton.tsx +0 -35
  92. package/src/components/Docs/HttpService/HttpService.spec.tsx +0 -429
  93. package/src/components/Docs/HttpService/HttpService.stories.ts +0 -14
  94. package/src/components/Docs/HttpService/HttpService.tsx +0 -99
  95. package/src/components/Docs/HttpService/SecuritySchemes.tsx +0 -82
  96. package/src/components/Docs/HttpService/ServerInfo.tsx +0 -196
  97. package/src/components/Docs/HttpService/index.ts +0 -1
  98. package/src/components/Docs/Model/Model.spec.tsx +0 -241
  99. package/src/components/Docs/Model/Model.stories.tsx +0 -16
  100. package/src/components/Docs/Model/Model.tsx +0 -192
  101. package/src/components/Docs/Model/index.ts +0 -1
  102. package/src/components/Docs/NodeVendorExtensions.tsx +0 -55
  103. package/src/components/Docs/Sections.tsx +0 -54
  104. package/src/components/Docs/Security/PanelContent.tsx +0 -38
  105. package/src/components/Docs/Security/index.ts +0 -1
  106. package/src/components/Docs/Skeleton.tsx +0 -12
  107. package/src/components/Docs/TwoColumnLayout.tsx +0 -27
  108. package/src/components/Docs/index.ts +0 -1
  109. package/src/components/Docs/story-helper.ts +0 -46
  110. package/src/components/Docs/story-renderer-helper.tsx +0 -56
  111. package/src/components/Layout/MobileTopNav.tsx +0 -78
  112. package/src/components/Layout/ResponsiveSidebarLayout.tsx +0 -175
  113. package/src/components/Layout/SidebarLayout.tsx +0 -107
  114. package/src/components/LinkHeading.tsx +0 -21
  115. package/src/components/LoadMore.tsx +0 -20
  116. package/src/components/Loading/Loading.tsx +0 -9
  117. package/src/components/Logo.tsx +0 -25
  118. package/src/components/MarkdownViewer/CustomComponents/CodeComponent.spec.ts +0 -90
  119. package/src/components/MarkdownViewer/CustomComponents/CodeComponent.tsx +0 -164
  120. package/src/components/MarkdownViewer/CustomComponents/Provider.tsx +0 -20
  121. package/src/components/MarkdownViewer/CustomComponents/ReactRouterLink.tsx +0 -27
  122. package/src/components/MarkdownViewer/CustomComponents/ResolvedImage.tsx +0 -86
  123. package/src/components/MarkdownViewer/CustomComponents/ScrollToHashElement.tsx +0 -96
  124. package/src/components/MarkdownViewer/MarkdownViewer.spec.tsx +0 -170
  125. package/src/components/MarkdownViewer/index.tsx +0 -10
  126. package/src/components/NonIdealState.tsx +0 -20
  127. package/src/components/PoweredByLink.tsx +0 -30
  128. package/src/components/RequestSamples/RequestSamples.stories.tsx +0 -67
  129. package/src/components/RequestSamples/RequestSamples.tsx +0 -246
  130. package/src/components/RequestSamples/__tests__/RequestSamples.test.tsx +0 -131
  131. package/src/components/RequestSamples/__tests__/__snapshots__/convertRequestToSample.spec.ts.snap +0 -746
  132. package/src/components/RequestSamples/__tests__/convertRequestToSample.spec.ts +0 -118
  133. package/src/components/RequestSamples/convertRequestToSample.ts +0 -56
  134. package/src/components/RequestSamples/extractCodeSamples.ts +0 -50
  135. package/src/components/RequestSamples/index.ts +0 -2
  136. package/src/components/RequestSamples/requestSampleConfigs.ts +0 -182
  137. package/src/components/ResponseExamples/ResponseExamples.spec.tsx +0 -121
  138. package/src/components/ResponseExamples/ResponseExamples.stories.tsx +0 -21
  139. package/src/components/ResponseExamples/ResponseExamples.tsx +0 -79
  140. package/src/components/TableOfContents/TableOfContents.spec.tsx +0 -301
  141. package/src/components/TableOfContents/TableOfContents.stories.tsx +0 -121
  142. package/src/components/TableOfContents/TableOfContents.tsx +0 -406
  143. package/src/components/TableOfContents/constants.ts +0 -45
  144. package/src/components/TableOfContents/index.ts +0 -2
  145. package/src/components/TableOfContents/types.ts +0 -51
  146. package/src/components/TableOfContents/utils.ts +0 -84
  147. package/src/components/TryIt/Auth/APIKeyAuth.tsx +0 -19
  148. package/src/components/TryIt/Auth/Auth.tsx +0 -169
  149. package/src/components/TryIt/Auth/AuthTokenInput.tsx +0 -37
  150. package/src/components/TryIt/Auth/BasicAuth.tsx +0 -62
  151. package/src/components/TryIt/Auth/BearerAuth.tsx +0 -19
  152. package/src/components/TryIt/Auth/DigestAuth.tsx +0 -35
  153. package/src/components/TryIt/Auth/OAuth2Auth.tsx +0 -19
  154. package/src/components/TryIt/Auth/authentication-utils.ts +0 -113
  155. package/src/components/TryIt/Body/BinaryBody.tsx +0 -52
  156. package/src/components/TryIt/Body/FormDataBody.tsx +0 -145
  157. package/src/components/TryIt/Body/RequestBody.tsx +0 -71
  158. package/src/components/TryIt/Body/__tests__/BinaryBody.test.tsx +0 -29
  159. package/src/components/TryIt/Body/__tests__/FormDataBody.test.tsx +0 -94
  160. package/src/components/TryIt/Body/request-body-utils.ts +0 -127
  161. package/src/components/TryIt/Body/useTextRequestBodyState.ts +0 -27
  162. package/src/components/TryIt/Mocking/MockingButton.tsx +0 -98
  163. package/src/components/TryIt/Mocking/mocking-utils.ts +0 -56
  164. package/src/components/TryIt/Mocking/useMockingOptions.ts +0 -6
  165. package/src/components/TryIt/Parameters/FileUploadParameterEditors.tsx +0 -62
  166. package/src/components/TryIt/Parameters/OperationParameters.tsx +0 -39
  167. package/src/components/TryIt/Parameters/ParameterEditor.tsx +0 -118
  168. package/src/components/TryIt/Parameters/__tests__/parameter-utils.spec.ts +0 -60
  169. package/src/components/TryIt/Parameters/parameter-utils.spec.ts +0 -118
  170. package/src/components/TryIt/Parameters/parameter-utils.ts +0 -179
  171. package/src/components/TryIt/Parameters/useOperationParameters.ts +0 -60
  172. package/src/components/TryIt/Response/ReponseCodeViewer.tsx +0 -28
  173. package/src/components/TryIt/Response/Response.spec.tsx +0 -174
  174. package/src/components/TryIt/Response/Response.tsx +0 -172
  175. package/src/components/TryIt/Response/hooks/useLineCount.ts +0 -7
  176. package/src/components/TryIt/Servers/ServerVariables.tsx +0 -33
  177. package/src/components/TryIt/Servers/ServersDropdown.tsx +0 -53
  178. package/src/components/TryIt/Servers/VariableEditor.tsx +0 -51
  179. package/src/components/TryIt/Servers/useServerVariables.ts +0 -19
  180. package/src/components/TryIt/TryIt.spec.tsx +0 -1511
  181. package/src/components/TryIt/TryIt.stories.tsx +0 -77
  182. package/src/components/TryIt/TryIt.tsx +0 -384
  183. package/src/components/TryIt/TryItWithRequestSamples.spec.tsx +0 -143
  184. package/src/components/TryIt/TryItWithRequestSamples.stories.tsx +0 -32
  185. package/src/components/TryIt/TryItWithRequestSamples.tsx +0 -42
  186. package/src/components/TryIt/build-request.spec.ts +0 -213
  187. package/src/components/TryIt/build-request.ts +0 -357
  188. package/src/components/TryIt/chosenServer.ts +0 -5
  189. package/src/components/TryIt/index.ts +0 -3
  190. package/src/components/__tests__/LinkHeading.spec.tsx +0 -125
  191. package/src/constants.ts +0 -176
  192. package/src/containers/MockingProvider.tsx +0 -23
  193. package/src/context/InlineRefResolver.spec.tsx +0 -183
  194. package/src/context/InlineRefResolver.tsx +0 -94
  195. package/src/context/Options.tsx +0 -27
  196. package/src/context/Persistence.tsx +0 -24
  197. package/src/context/RouterType.tsx +0 -9
  198. package/src/core.css +0 -97
  199. package/src/hoc/utils.ts +0 -5
  200. package/src/hoc/withMosaicProvider.spec.tsx +0 -48
  201. package/src/hoc/withMosaicProvider.tsx +0 -28
  202. package/src/hoc/withQueryClientProvider.spec.tsx +0 -38
  203. package/src/hoc/withQueryClientProvider.tsx +0 -35
  204. package/src/hoc/withRouter.tsx +0 -71
  205. package/src/hooks/useBundleRefsIntoDocument.ts +0 -60
  206. package/src/hooks/useFirstRender.ts +0 -8
  207. package/src/hooks/useIsCompact.ts +0 -26
  208. package/src/hooks/useParsedData.ts +0 -99
  209. package/src/hooks/useParsedValue.ts +0 -19
  210. package/src/hooks/useResponsiveLayout.tsx +0 -51
  211. package/src/hooks/useRouter.tsx +0 -31
  212. package/src/hooks/useUniqueId.ts +0 -4
  213. package/src/index.ts +0 -48
  214. package/src/styled.tsx +0 -22
  215. package/src/styles.css +0 -4
  216. package/src/types.ts +0 -170
  217. package/src/utils/__tests__/securitySchemes.spec.ts +0 -137
  218. package/src/utils/exampleGeneration/exampleGeneration.spec.tsx +0 -18
  219. package/src/utils/exampleGeneration/exampleGeneration.ts +0 -110
  220. package/src/utils/fileToBase64.ts +0 -11
  221. package/src/utils/guards.ts +0 -48
  222. package/src/utils/headers.ts +0 -316
  223. package/src/utils/http-spec/IServer.ts +0 -100
  224. package/src/utils/http-spec/__tests__/IServer.spec.ts +0 -51
  225. package/src/utils/http-spec/examples.ts +0 -5
  226. package/src/utils/http.ts +0 -9
  227. package/src/utils/jotai/persistAtom.ts +0 -31
  228. package/src/utils/node.ts +0 -19
  229. package/src/utils/oas/__tests__/security.spec.ts +0 -18
  230. package/src/utils/oas/security.ts +0 -76
  231. package/src/utils/ref-resolving/ReferenceResolver.ts +0 -29
  232. package/src/utils/ref-resolving/resolvedObject.test.ts +0 -415
  233. package/src/utils/ref-resolving/resolvedObject.ts +0 -109
  234. package/src/utils/securitySchemes.ts +0 -117
  235. package/src/utils/string.ts +0 -15
  236. package/src/utils/tests/chooseOption.ts +0 -7
  237. package/src/web-components/createElementClass.ts +0 -154
  238. package/tsconfig.build.json +0 -14
  239. package/tsconfig.json +0 -7
  240. /package/{dist/__fixtures__ → __fixtures__}/articles/schema-with-refs.d.ts +0 -0
  241. /package/{dist/__fixtures__ → __fixtures__}/operations/application-octet-stream-post.d.ts +0 -0
  242. /package/{dist/__fixtures__ → __fixtures__}/operations/base64-file-upload.d.ts +0 -0
  243. /package/{dist/__fixtures__ → __fixtures__}/operations/big-response.d.ts +0 -0
  244. /package/{dist/__fixtures__ → __fixtures__}/operations/examples-request-body.d.ts +0 -0
  245. /package/{dist/__fixtures__ → __fixtures__}/operations/head-todos.d.ts +0 -0
  246. /package/{dist/__fixtures__ → __fixtures__}/operations/multipart-formdata-post.d.ts +0 -0
  247. /package/{dist/__fixtures__ → __fixtures__}/operations/operation-minimal.d.ts +0 -0
  248. /package/{dist/__fixtures__ → __fixtures__}/operations/operation-parameters.d.ts +0 -0
  249. /package/{dist/__fixtures__ → __fixtures__}/operations/operation-with-examples.d.ts +0 -0
  250. /package/{dist/__fixtures__ → __fixtures__}/operations/operation-without-servers.d.ts +0 -0
  251. /package/{dist/__fixtures__ → __fixtures__}/operations/patch-todos.d.ts +0 -0
  252. /package/{dist/__fixtures__ → __fixtures__}/operations/put-todos.d.ts +0 -0
  253. /package/{dist/__fixtures__ → __fixtures__}/operations/referenced-body.d.ts +0 -0
  254. /package/{dist/__fixtures__ → __fixtures__}/operations/request-body-empty-schema.d.ts +0 -0
  255. /package/{dist/__fixtures__ → __fixtures__}/operations/request-body.d.ts +0 -0
  256. /package/{dist/__fixtures__ → __fixtures__}/operations/securedOperation.d.ts +0 -0
  257. /package/{dist/__fixtures__ → __fixtures__}/operations/security-basic.d.ts +0 -0
  258. /package/{dist/__fixtures__ → __fixtures__}/operations/security-bearer.d.ts +0 -0
  259. /package/{dist/__fixtures__ → __fixtures__}/operations/simple-get.d.ts +0 -0
  260. /package/{dist/__fixtures__ → __fixtures__}/operations/string-numeric-enums.d.ts +0 -0
  261. /package/{dist/__fixtures__ → __fixtures__}/operations/urlencoded-post-oneof.d.ts +0 -0
  262. /package/{dist/__fixtures__ → __fixtures__}/operations/urlencoded-post.d.ts +0 -0
  263. /package/{dist/__fixtures__ → __fixtures__}/operations/with-url-variables.d.ts +0 -0
  264. /package/{dist/__fixtures__ → __fixtures__}/security-schemes/index.d.ts +0 -0
  265. /package/{dist/__fixtures__ → __fixtures__}/services/petstore.d.ts +0 -0
  266. /package/{dist/__fixtures__ → __fixtures__}/services/with-unnamed-servers.d.ts +0 -0
  267. /package/{dist/__fixtures__ → __fixtures__}/services/with-url-variables.d.ts +0 -0
  268. /package/{dist/__fixtures__ → __fixtures__}/services/without-origin.d.ts +0 -0
  269. /package/{dist/components → components}/Docs/Article/Article.spec.d.ts +0 -0
  270. /package/{dist/components → components}/Docs/Article/Article.stories.d.ts +0 -0
  271. /package/{dist/components → components}/Docs/Article/index.d.ts +0 -0
  272. /package/{dist/components → components}/Docs/Docs.stories.d.ts +0 -0
  273. /package/{dist/components → components}/Docs/HttpOperation/Badges.d.ts +0 -0
  274. /package/{dist/components → components}/Docs/HttpOperation/Callbacks.d.ts +0 -0
  275. /package/{dist/components → components}/Docs/HttpOperation/HttpOperation.spec.d.ts +0 -0
  276. /package/{dist/components → components}/Docs/HttpOperation/HttpOperation.stories.d.ts +0 -0
  277. /package/{dist/components → components}/Docs/HttpOperation/Parameters.d.ts +0 -0
  278. /package/{dist/components → components}/Docs/HttpOperation/Parameters.spec.d.ts +0 -0
  279. /package/{dist/components → components}/Docs/HttpOperation/index.d.ts +0 -0
  280. /package/{dist/components → components}/Docs/HttpService/AdditionalInfo.d.ts +0 -0
  281. /package/{dist/components → components}/Docs/HttpService/AdditionalInfo.stories.d.ts +0 -0
  282. /package/{dist/components → components}/Docs/HttpService/ExportButton.d.ts +0 -0
  283. /package/{dist/components → components}/Docs/HttpService/HttpService.d.ts +0 -0
  284. /package/{dist/components → components}/Docs/HttpService/HttpService.spec.d.ts +0 -0
  285. /package/{dist/components → components}/Docs/HttpService/HttpService.stories.d.ts +0 -0
  286. /package/{dist/components → components}/Docs/HttpService/SecuritySchemes.d.ts +0 -0
  287. /package/{dist/components → components}/Docs/HttpService/ServerInfo.d.ts +0 -0
  288. /package/{dist/components → components}/Docs/HttpService/index.d.ts +0 -0
  289. /package/{dist/components → components}/Docs/Model/Model.d.ts +0 -0
  290. /package/{dist/components → components}/Docs/Model/Model.spec.d.ts +0 -0
  291. /package/{dist/components → components}/Docs/Model/Model.stories.d.ts +0 -0
  292. /package/{dist/components → components}/Docs/Model/index.d.ts +0 -0
  293. /package/{dist/components → components}/Docs/NodeVendorExtensions.d.ts +0 -0
  294. /package/{dist/components → components}/Docs/Sections.d.ts +0 -0
  295. /package/{dist/components → components}/Docs/Security/PanelContent.d.ts +0 -0
  296. /package/{dist/components → components}/Docs/Security/index.d.ts +0 -0
  297. /package/{dist/components → components}/Docs/Skeleton.d.ts +0 -0
  298. /package/{dist/components → components}/Docs/TwoColumnLayout.d.ts +0 -0
  299. /package/{dist/components → components}/Docs/index.d.ts +0 -0
  300. /package/{dist/components → components}/Docs/story-helper.d.ts +0 -0
  301. /package/{dist/components → components}/Docs/story-renderer-helper.d.ts +0 -0
  302. /package/{dist/components → components}/Layout/MobileTopNav.d.ts +0 -0
  303. /package/{dist/components → components}/Layout/ResponsiveSidebarLayout.d.ts +0 -0
  304. /package/{dist/components → components}/Layout/SidebarLayout.d.ts +0 -0
  305. /package/{dist/components → components}/LinkHeading.d.ts +0 -0
  306. /package/{dist/components → components}/LoadMore.d.ts +0 -0
  307. /package/{dist/components → components}/Loading/Loading.d.ts +0 -0
  308. /package/{dist/components → components}/Logo.d.ts +0 -0
  309. /package/{dist/components → components}/MarkdownViewer/CustomComponents/CodeComponent.d.ts +0 -0
  310. /package/{dist/components → components}/MarkdownViewer/CustomComponents/CodeComponent.spec.d.ts +0 -0
  311. /package/{dist/components → components}/MarkdownViewer/CustomComponents/Provider.d.ts +0 -0
  312. /package/{dist/components → components}/MarkdownViewer/CustomComponents/ReactRouterLink.d.ts +0 -0
  313. /package/{dist/components → components}/MarkdownViewer/CustomComponents/ResolvedImage.d.ts +0 -0
  314. /package/{dist/components → components}/MarkdownViewer/CustomComponents/ScrollToHashElement.d.ts +0 -0
  315. /package/{dist/components → components}/MarkdownViewer/MarkdownViewer.spec.d.ts +0 -0
  316. /package/{dist/components → components}/MarkdownViewer/index.d.ts +0 -0
  317. /package/{dist/components → components}/NonIdealState.d.ts +0 -0
  318. /package/{dist/components → components}/PoweredByLink.d.ts +0 -0
  319. /package/{dist/components → components}/RequestSamples/RequestSamples.d.ts +0 -0
  320. /package/{dist/components → components}/RequestSamples/RequestSamples.stories.d.ts +0 -0
  321. /package/{dist/components → components}/RequestSamples/convertRequestToSample.d.ts +0 -0
  322. /package/{dist/components → components}/RequestSamples/extractCodeSamples.d.ts +0 -0
  323. /package/{dist/components → components}/RequestSamples/index.d.ts +0 -0
  324. /package/{dist/components → components}/RequestSamples/requestSampleConfigs.d.ts +0 -0
  325. /package/{dist/components → components}/ResponseExamples/ResponseExamples.d.ts +0 -0
  326. /package/{dist/components → components}/ResponseExamples/ResponseExamples.spec.d.ts +0 -0
  327. /package/{dist/components → components}/ResponseExamples/ResponseExamples.stories.d.ts +0 -0
  328. /package/{dist/components → components}/TableOfContents/TableOfContents.d.ts +0 -0
  329. /package/{dist/components → components}/TableOfContents/TableOfContents.spec.d.ts +0 -0
  330. /package/{dist/components → components}/TableOfContents/TableOfContents.stories.d.ts +0 -0
  331. /package/{dist/components → components}/TableOfContents/constants.d.ts +0 -0
  332. /package/{dist/components → components}/TableOfContents/index.d.ts +0 -0
  333. /package/{dist/components → components}/TableOfContents/utils.d.ts +0 -0
  334. /package/{dist/components → components}/TryIt/Auth/APIKeyAuth.d.ts +0 -0
  335. /package/{dist/components → components}/TryIt/Auth/Auth.d.ts +0 -0
  336. /package/{dist/components → components}/TryIt/Auth/AuthTokenInput.d.ts +0 -0
  337. /package/{dist/components → components}/TryIt/Auth/BasicAuth.d.ts +0 -0
  338. /package/{dist/components → components}/TryIt/Auth/BearerAuth.d.ts +0 -0
  339. /package/{dist/components → components}/TryIt/Auth/DigestAuth.d.ts +0 -0
  340. /package/{dist/components → components}/TryIt/Auth/OAuth2Auth.d.ts +0 -0
  341. /package/{dist/components → components}/TryIt/Auth/authentication-utils.d.ts +0 -0
  342. /package/{dist/components → components}/TryIt/Body/BinaryBody.d.ts +0 -0
  343. /package/{dist/components → components}/TryIt/Body/FormDataBody.d.ts +0 -0
  344. /package/{dist/components → components}/TryIt/Body/RequestBody.d.ts +0 -0
  345. /package/{dist/components → components}/TryIt/Body/request-body-utils.d.ts +0 -0
  346. /package/{dist/components → components}/TryIt/Body/useTextRequestBodyState.d.ts +0 -0
  347. /package/{dist/components → components}/TryIt/Mocking/MockingButton.d.ts +0 -0
  348. /package/{dist/components → components}/TryIt/Mocking/mocking-utils.d.ts +0 -0
  349. /package/{dist/components → components}/TryIt/Mocking/useMockingOptions.d.ts +0 -0
  350. /package/{dist/components → components}/TryIt/Parameters/FileUploadParameterEditors.d.ts +0 -0
  351. /package/{dist/components → components}/TryIt/Parameters/OperationParameters.d.ts +0 -0
  352. /package/{dist/components → components}/TryIt/Parameters/ParameterEditor.d.ts +0 -0
  353. /package/{dist/components → components}/TryIt/Parameters/parameter-utils.d.ts +0 -0
  354. /package/{dist/components → components}/TryIt/Parameters/parameter-utils.spec.d.ts +0 -0
  355. /package/{dist/components → components}/TryIt/Parameters/useOperationParameters.d.ts +0 -0
  356. /package/{dist/components → components}/TryIt/Response/ReponseCodeViewer.d.ts +0 -0
  357. /package/{dist/components → components}/TryIt/Response/Response.d.ts +0 -0
  358. /package/{dist/components → components}/TryIt/Response/Response.spec.d.ts +0 -0
  359. /package/{dist/components → components}/TryIt/Response/hooks/useLineCount.d.ts +0 -0
  360. /package/{dist/components → components}/TryIt/Servers/ServerVariables.d.ts +0 -0
  361. /package/{dist/components → components}/TryIt/Servers/ServersDropdown.d.ts +0 -0
  362. /package/{dist/components → components}/TryIt/Servers/VariableEditor.d.ts +0 -0
  363. /package/{dist/components → components}/TryIt/Servers/useServerVariables.d.ts +0 -0
  364. /package/{dist/components → components}/TryIt/TryIt.d.ts +0 -0
  365. /package/{dist/components → components}/TryIt/TryIt.spec.d.ts +0 -0
  366. /package/{dist/components → components}/TryIt/TryIt.stories.d.ts +0 -0
  367. /package/{dist/components → components}/TryIt/TryItWithRequestSamples.d.ts +0 -0
  368. /package/{dist/components → components}/TryIt/TryItWithRequestSamples.spec.d.ts +0 -0
  369. /package/{dist/components → components}/TryIt/TryItWithRequestSamples.stories.d.ts +0 -0
  370. /package/{dist/components → components}/TryIt/build-request.d.ts +0 -0
  371. /package/{dist/components → components}/TryIt/build-request.spec.d.ts +0 -0
  372. /package/{dist/components → components}/TryIt/chosenServer.d.ts +0 -0
  373. /package/{dist/components → components}/TryIt/index.d.ts +0 -0
  374. /package/{dist/constants.d.ts → constants.d.ts} +0 -0
  375. /package/{dist/containers → containers}/MockingProvider.d.ts +0 -0
  376. /package/{dist/context → context}/InlineRefResolver.d.ts +0 -0
  377. /package/{dist/context → context}/InlineRefResolver.spec.d.ts +0 -0
  378. /package/{dist/context → context}/Options.d.ts +0 -0
  379. /package/{dist/context → context}/Persistence.d.ts +0 -0
  380. /package/{dist/context → context}/RouterType.d.ts +0 -0
  381. /package/{dist/core.css → core.css} +0 -0
  382. /package/{dist/hoc → hoc}/utils.d.ts +0 -0
  383. /package/{dist/hoc → hoc}/withMosaicProvider.d.ts +0 -0
  384. /package/{dist/hoc → hoc}/withMosaicProvider.spec.d.ts +0 -0
  385. /package/{dist/hoc → hoc}/withQueryClientProvider.d.ts +0 -0
  386. /package/{dist/hoc → hoc}/withQueryClientProvider.spec.d.ts +0 -0
  387. /package/{dist/hoc → hoc}/withRouter.d.ts +0 -0
  388. /package/{dist/hooks → hooks}/useBundleRefsIntoDocument.d.ts +0 -0
  389. /package/{dist/hooks → hooks}/useFirstRender.d.ts +0 -0
  390. /package/{dist/hooks → hooks}/useIsCompact.d.ts +0 -0
  391. /package/{dist/hooks → hooks}/useParsedData.d.ts +0 -0
  392. /package/{dist/hooks → hooks}/useParsedValue.d.ts +0 -0
  393. /package/{dist/hooks → hooks}/useResponsiveLayout.d.ts +0 -0
  394. /package/{dist/hooks → hooks}/useRouter.d.ts +0 -0
  395. /package/{dist/hooks → hooks}/useUniqueId.d.ts +0 -0
  396. /package/{dist/index.d.ts → index.d.ts} +0 -0
  397. /package/{dist/styled.d.ts → styled.d.ts} +0 -0
  398. /package/{dist/styles.min.css → styles.min.css} +0 -0
  399. /package/{dist/types.d.ts → types.d.ts} +0 -0
  400. /package/{dist/utils → utils}/exampleGeneration/exampleGeneration.d.ts +0 -0
  401. /package/{dist/utils → utils}/exampleGeneration/exampleGeneration.spec.d.ts +0 -0
  402. /package/{dist/utils → utils}/fileToBase64.d.ts +0 -0
  403. /package/{dist/utils → utils}/guards.d.ts +0 -0
  404. /package/{dist/utils → utils}/headers.d.ts +0 -0
  405. /package/{dist/utils → utils}/http-spec/IServer.d.ts +0 -0
  406. /package/{dist/utils → utils}/http-spec/examples.d.ts +0 -0
  407. /package/{dist/utils → utils}/http.d.ts +0 -0
  408. /package/{dist/utils → utils}/jotai/persistAtom.d.ts +0 -0
  409. /package/{dist/utils → utils}/node.d.ts +0 -0
  410. /package/{dist/utils → utils}/oas/security.d.ts +0 -0
  411. /package/{dist/utils → utils}/ref-resolving/ReferenceResolver.d.ts +0 -0
  412. /package/{dist/utils → utils}/ref-resolving/resolvedObject.d.ts +0 -0
  413. /package/{dist/utils → utils}/ref-resolving/resolvedObject.test.d.ts +0 -0
  414. /package/{dist/utils → utils}/securitySchemes.d.ts +0 -0
  415. /package/{dist/utils → utils}/string.d.ts +0 -0
  416. /package/{dist/utils → utils}/tests/chooseOption.d.ts +0 -0
  417. /package/{dist/web-components → web-components}/createElementClass.d.ts +0 -0
@@ -1,1511 +0,0 @@
1
- import '@testing-library/jest-dom';
2
-
3
- import { Provider as MosaicProvider } from '@stoplight/mosaic';
4
- import { HttpParamStyles, IHttpOperation } from '@stoplight/types';
5
- import { cleanup, render, screen, waitFor } from '@testing-library/react';
6
- import userEvent from '@testing-library/user-event';
7
- import fetchMock from 'jest-fetch-mock';
8
- import * as React from 'react';
9
-
10
- import { httpOperation as octetStreamOperation } from '../../__fixtures__/operations/application-octet-stream-post';
11
- import { httpOperation as base64FileUpload } from '../../__fixtures__/operations/base64-file-upload';
12
- import { examplesRequestBody, singleExampleRequestBody } from '../../__fixtures__/operations/examples-request-body';
13
- import { headWithRequestBody } from '../../__fixtures__/operations/head-todos';
14
- import { httpOperation as multipartFormdataOperation } from '../../__fixtures__/operations/multipart-formdata-post';
15
- import { httpOperation as sortedParameters } from '../../__fixtures__/operations/operation-parameters';
16
- import { operation as operationWithoutServers } from '../../__fixtures__/operations/operation-without-servers';
17
- import { patchWithRequestBody } from '../../__fixtures__/operations/patch-todos';
18
- import { httpOperation as putOperation } from '../../__fixtures__/operations/put-todos';
19
- import { httpOperation as referencedBody } from '../../__fixtures__/operations/referenced-body';
20
- import { requestBody } from '../../__fixtures__/operations/request-body';
21
- import { requestBodyEmptySchema } from '../../__fixtures__/operations/request-body-empty-schema';
22
- import {
23
- duplicatedSecurityScheme,
24
- emptySecurityOperation,
25
- singleSecurityOperation,
26
- } from '../../__fixtures__/operations/securedOperation';
27
- import { httpOperation as basicSecurityOperation } from '../../__fixtures__/operations/security-basic';
28
- import { httpOperation as bearerSecurityOperation } from '../../__fixtures__/operations/security-bearer';
29
- import { operation as basicOperation } from '../../__fixtures__/operations/simple-get';
30
- import { httpOperation as stringNumericEnumOperation } from '../../__fixtures__/operations/string-numeric-enums';
31
- import { httpOperation as urlEncodedPostOperation } from '../../__fixtures__/operations/urlencoded-post';
32
- import { operationWithUrlVariables } from '../../__fixtures__/operations/with-url-variables';
33
- import { InlineRefResolverProvider } from '../../context/InlineRefResolver';
34
- import { PersistenceContextProvider, withPersistenceBoundary } from '../../context/Persistence';
35
- import { withMosaicProvider } from '../../hoc/withMosaicProvider';
36
- import { chooseOption } from '../../utils/tests/chooseOption';
37
- import { TryIt } from './index';
38
-
39
- function clickSend() {
40
- const button = screen.getByRole('button', { name: /send/i });
41
- userEvent.click(button);
42
- }
43
-
44
- const TryItWithPersistence = withMosaicProvider(withPersistenceBoundary(TryIt));
45
-
46
- describe('TryIt', () => {
47
- beforeEach(() => {
48
- fetchMock.resetMocks();
49
- localStorage.clear();
50
- });
51
-
52
- it("Doesn't crash", () => {
53
- render(<TryItWithPersistence httpOperation={basicOperation} />);
54
- });
55
-
56
- it('Makes the correct basic request', async () => {
57
- render(<TryItWithPersistence httpOperation={basicOperation} />);
58
-
59
- clickSend();
60
-
61
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
62
- expect(fetchMock.mock.calls[0][0]).toBe('https://todos.stoplight.io/todos');
63
- const requestInit = fetchMock.mock.calls[0][1]!;
64
- expect(requestInit.method).toMatch(/^get$/i);
65
- const headers = new Headers(requestInit.headers);
66
- expect(headers.get('Content-Type')).toBe(null);
67
- });
68
-
69
- it('uses cors proxy url, if provided', async () => {
70
- render(<TryItWithPersistence httpOperation={basicOperation} corsProxy="https://some.proxy.com/" />);
71
-
72
- clickSend();
73
-
74
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
75
- expect(fetchMock.mock.calls[0][0]).toBe('https://some.proxy.com/https://todos.stoplight.io/todos');
76
- });
77
-
78
- it('replaces url variables with default values when making request', async () => {
79
- render(<TryItWithPersistence httpOperation={operationWithUrlVariables} />);
80
-
81
- const button = screen.getByRole('button', { name: /send/i });
82
- userEvent.click(button);
83
-
84
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
85
- expect(fetchMock.mock.calls[0][0]).toBe('ftp://default-namespace.stoplight.io/api/eu/todos');
86
- });
87
-
88
- it('makes request to origin URL if there is no URL in the document', async () => {
89
- render(<TryItWithPersistence httpOperation={operationWithoutServers} />);
90
-
91
- const button = screen.getByRole('button', { name: /send/i });
92
- userEvent.click(button);
93
-
94
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
95
- expect(fetchMock.mock.calls[0][0]).toBe('http://localhost/todos');
96
- });
97
-
98
- it('Displays response', async () => {
99
- fetchMock.mockResolvedValue(
100
- new Response('{}', {
101
- status: 200,
102
- statusText: 'OK',
103
- headers: [],
104
- }),
105
- );
106
-
107
- render(<TryItWithPersistence httpOperation={basicOperation} />);
108
-
109
- let responseHeader = screen.queryByText('Response');
110
- expect(responseHeader).not.toBeInTheDocument();
111
-
112
- clickSend();
113
-
114
- responseHeader = await screen.findByText('Response');
115
- expect(responseHeader).toBeVisible();
116
- });
117
-
118
- it('displays raw text response', async () => {
119
- fetchMock.mockResolvedValue(
120
- new Response('awesome response, but hardly a json one', {
121
- status: 200,
122
- statusText: 'OK',
123
- headers: [],
124
- }),
125
- );
126
-
127
- const { container } = render(<TryItWithPersistence httpOperation={basicOperation} />);
128
-
129
- clickSend();
130
-
131
- await screen.findByText('Response');
132
-
133
- expect(container).toHaveTextContent('awesome response, but hardly a json one');
134
- });
135
-
136
- it('Handles error', async () => {
137
- fetchMock.mockReject(new Error('sample error'));
138
-
139
- render(<TryItWithPersistence httpOperation={basicOperation} />);
140
-
141
- let errorHeader = screen.queryByText('Error');
142
- expect(errorHeader).not.toBeInTheDocument();
143
-
144
- clickSend();
145
-
146
- errorHeader = await screen.findByText('Error');
147
- expect(errorHeader).toBeVisible();
148
-
149
- const responseHeader = screen.queryByText('Response');
150
- expect(responseHeader).not.toBeInTheDocument();
151
- });
152
-
153
- it('when embedded in markdown, shows request codegen', async () => {
154
- render(<TryItWithPersistence httpOperation={basicOperation} embeddedInMd />);
155
-
156
- const requestSamplePanel = await screen.findByText('Request Sample: Shell / cURL');
157
- expect(requestSamplePanel).toBeVisible();
158
- });
159
-
160
- describe('Credentials policy', () => {
161
- it('sets credentials correctly', async () => {
162
- render(<TryItWithPersistence httpOperation={basicOperation} tryItCredentialsPolicy="same-origin" />);
163
-
164
- const button = screen.getByRole('button', { name: /send/i });
165
- userEvent.click(button);
166
-
167
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
168
- const requestInit = fetchMock.mock.calls[0][1]!;
169
- expect(requestInit.credentials).toEqual('same-origin');
170
- });
171
-
172
- it('use `omit` as default credentials policy', async () => {
173
- render(<TryItWithPersistence httpOperation={basicOperation} />);
174
-
175
- const button = screen.getByRole('button', { name: /send/i });
176
- userEvent.click(button);
177
-
178
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
179
- const requestInit = fetchMock.mock.calls[0][1]!;
180
- expect(requestInit.credentials).toEqual('omit');
181
- });
182
- });
183
-
184
- describe('Parameter Handling', () => {
185
- it('Hides panel when there are no parameters', () => {
186
- render(<TryItWithPersistence httpOperation={basicOperation} />);
187
-
188
- let parametersHeader = screen.queryByText('Parameters');
189
- expect(parametersHeader).not.toBeInTheDocument();
190
- });
191
-
192
- it('Shows panel when there are parameters', () => {
193
- render(<TryItWithPersistence httpOperation={putOperation} />);
194
-
195
- let parametersHeader = screen.queryByText('Parameters');
196
- expect(parametersHeader).toBeInTheDocument();
197
- });
198
-
199
- describe('Sorts parameters alphabetically', () => {
200
- it('by type and put required one on top for each type', () => {
201
- const names = [
202
- 'todoId*',
203
- 'anotherId',
204
- 'bAnotherId',
205
- 'limit*',
206
- 'super_duper_long_parameter_name_with_unnecessary_text*',
207
- 'completed',
208
- 'deep_object',
209
- 'default_style_items',
210
- 'items',
211
- 'items_not_exploded',
212
- 'items_pipes',
213
- 'items_pipes_not_exploded',
214
- 'items_spaces',
215
- 'items_spaces_not_exploded',
216
- 'nested',
217
- 'nested_not_exploded',
218
- 'optional_value_with_default',
219
- 'type',
220
- 'value',
221
- 'message-id*',
222
- 'account-id',
223
- 'b-account-id',
224
- ];
225
- render(<TryItWithPersistence httpOperation={sortedParameters} />);
226
-
227
- const params = screen.queryAllByTestId('param-label').map(element => element.textContent);
228
- expect(params).toEqual(names);
229
- });
230
- });
231
-
232
- it('Displays types correctly', () => {
233
- render(<TryItWithPersistence httpOperation={putOperation} />);
234
-
235
- const todoIdField = screen.getByLabelText('todoId') as HTMLInputElement;
236
- expect(todoIdField.placeholder).toMatch(/string/i);
237
- });
238
-
239
- it('Initializes parameters correctly', () => {
240
- render(<TryItWithPersistence httpOperation={putOperation} />);
241
-
242
- // path param
243
- const completedField = screen.getByLabelText('completed');
244
- expect(completedField).toHaveValue('');
245
- expect(completedField).toHaveTextContent('select an option');
246
-
247
- // query params
248
- const limitField = screen.getByLabelText('limit');
249
- expect(limitField).toHaveTextContent('select an option (defaults to: 1)');
250
-
251
- const typeField = screen.getByLabelText('type');
252
- expect(typeField).toHaveTextContent('something');
253
-
254
- const optionalWithDefaultField = screen.getByLabelText('optional_value_with_default') as HTMLInputElement;
255
- expect(optionalWithDefaultField).toHaveValue('');
256
- expect(optionalWithDefaultField.placeholder).toBe('defaults to: some default value');
257
-
258
- const valueField = screen.getByLabelText('value');
259
- expect(valueField).toHaveTextContent('1');
260
-
261
- // header param
262
-
263
- const accountIdField = screen.getByLabelText('account-id') as HTMLInputElement;
264
- expect(accountIdField).toHaveValue('account-id-default');
265
- expect(accountIdField.placeholder).toBe('defaults to: account-id-default');
266
-
267
- const messageIdField = screen.getByLabelText('message-id');
268
- expect(messageIdField).toHaveValue('example value');
269
- });
270
-
271
- it('Passes all parameters to the request', async () => {
272
- render(<TryItWithPersistence httpOperation={putOperation} />);
273
-
274
- // path param
275
- const todoIdField = screen.getByLabelText('todoId');
276
- userEvent.type(todoIdField, '123');
277
-
278
- // query params
279
- const limitField = screen.getByLabelText('limit');
280
- chooseOption(limitField, '3');
281
-
282
- const typeField = screen.getByLabelText('type');
283
- chooseOption(typeField, 'another');
284
-
285
- const pairsField = screen.getByLabelText('pairs');
286
- userEvent.type(pairsField, '{ "nestedKey": "nestedValue" }');
287
-
288
- const pagination = screen.getByLabelText('pagination');
289
- userEvent.type(pagination, '{ "first": 50, "after": "cursor" }');
290
-
291
- const itemsField = screen.getByLabelText('items');
292
- userEvent.type(itemsField, '["first", "second"]');
293
-
294
- // header param
295
-
296
- const accountIdField = screen.getByLabelText('account-id');
297
- userEvent.type(accountIdField, ' 1999');
298
-
299
- const messageIdField = screen.getByLabelText('message-id-select');
300
- chooseOption(messageIdField, 'example 2');
301
-
302
- const quoteField = screen.getByLabelText('quote-select');
303
- chooseOption(quoteField, 'quote');
304
-
305
- // click send
306
- clickSend();
307
-
308
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
309
- const url = new URL(fetchMock.mock.calls[0][0] as string);
310
- // assert that path params are passed
311
- expect(url.pathname.endsWith('123'));
312
- const queryParams = url.searchParams;
313
- // assert that query params are passed
314
- expect(queryParams.get('limit')).toBe('3');
315
- expect(queryParams.get('value')).toBe('1');
316
- expect(queryParams.get('type')).toBe('another');
317
- expect(queryParams.get('optional_value_with_default')).toBeNull();
318
- expect(queryParams.get('nestedKey')).toBe('nestedValue');
319
- expect(queryParams.get('pairs')).toBeNull();
320
- expect(queryParams.get('pagination[first]')).toBe('50');
321
- expect(queryParams.get('pagination[after]')).toBe('cursor');
322
- expect(queryParams.getAll('items')).toEqual(['first', 'second']);
323
- // assert that headers are passed
324
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
325
- expect(headers.get('Content-Type')).toBe('application/json');
326
- expect(headers.get('account-id')).toBe('account-id-default 1999');
327
- expect(headers.get('message-id')).toBe('another example');
328
- expect(headers.get('optional_header')).toBeNull();
329
-
330
- // assert that quote is escaped
331
- expect(headers.get('quote')).toBe('\\"');
332
- });
333
-
334
- it('Persists parameter values between operations', async () => {
335
- const { rerender } = render(
336
- <PersistenceContextProvider>
337
- <TryIt httpOperation={putOperation} />
338
- </PersistenceContextProvider>,
339
- );
340
-
341
- // fill path param
342
- const todoIdField = screen.getByLabelText('todoId');
343
- userEvent.type(todoIdField, '123');
344
-
345
- // unmount (to make sure parameters are not simply stored in component state)
346
- rerender(
347
- <PersistenceContextProvider>
348
- <div />
349
- </PersistenceContextProvider>,
350
- );
351
-
352
- // mount a different instance
353
-
354
- const alternativeSchema: IHttpOperation = {
355
- id: 'patch',
356
- method: 'patch',
357
- path: '/todos/{todoId}',
358
- responses: [],
359
- servers: [
360
- {
361
- id: '?http-server?',
362
- url: 'https://todos.stoplight.io',
363
- },
364
- ],
365
- request: {
366
- path: [
367
- {
368
- id: '?http-path-param-todoId?',
369
- schema: {
370
- type: 'string',
371
- },
372
- name: 'todoId',
373
- style: HttpParamStyles.Simple,
374
- required: true,
375
- },
376
- ],
377
- },
378
- };
379
-
380
- rerender(
381
- <PersistenceContextProvider>
382
- <TryIt httpOperation={alternativeSchema} />
383
- </PersistenceContextProvider>,
384
- );
385
-
386
- expect(screen.getByLabelText('todoId')).toHaveValue('123');
387
- });
388
-
389
- it('Persists string enum types', () => {
390
- render(<TryItWithPersistence httpOperation={stringNumericEnumOperation} />);
391
-
392
- const cycleField = screen.getByLabelText('cycle');
393
- expect(cycleField).toHaveTextContent('00');
394
-
395
- userEvent.click(cycleField);
396
-
397
- userEvent.click(screen.getByRole('option', { name: '06' }));
398
- expect(cycleField).toHaveTextContent('06');
399
- });
400
- });
401
-
402
- describe('Form Data Body', () => {
403
- it('Hides panel when there are no parameters', () => {
404
- render(<TryItWithPersistence httpOperation={basicOperation} />);
405
-
406
- let parametersHeader = screen.queryByText('Body');
407
- expect(parametersHeader).not.toBeInTheDocument();
408
- });
409
-
410
- it('Shows panel when there are parameters', () => {
411
- render(<TryItWithPersistence httpOperation={urlEncodedPostOperation} />);
412
-
413
- let parametersHeader = screen.queryByText('Body');
414
- expect(parametersHeader).toBeInTheDocument();
415
- });
416
-
417
- it('Displays types correctly', () => {
418
- render(<TryItWithPersistence httpOperation={urlEncodedPostOperation} />);
419
-
420
- const nameField = screen.getByRole('textbox', { name: 'name' }) as HTMLInputElement;
421
- expect(nameField.placeholder).toMatch(/string/i);
422
-
423
- const completedField = screen.getByLabelText('completed');
424
- expect(completedField).toBeInTheDocument();
425
- });
426
-
427
- it('allows to omit empty value', async () => {
428
- render(<TryItWithPersistence httpOperation={multipartFormdataOperation} />);
429
-
430
- const ageField = screen.getByRole('textbox', { name: 'age' }) as HTMLInputElement;
431
- await userEvent.type(ageField, '12');
432
-
433
- const checkboxName = screen.getByRole('checkbox', { name: 'age-checkbox' }) as HTMLInputElement;
434
- await userEvent.click(checkboxName);
435
-
436
- clickSend();
437
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
438
-
439
- const body = fetchMock.mock.calls[0][1]!.body as FormData;
440
- expect(body.has('age')).toBe(false);
441
- expect(body.has('name')).toBe(true);
442
- });
443
-
444
- const formDataCases: ReadonlyArray<[string, NewableFunction, IHttpOperation]> = [
445
- ['application/x-www-form-urlencoded', URLSearchParams, urlEncodedPostOperation],
446
- ['multipart/form-data', FormData, multipartFormdataOperation],
447
- ];
448
-
449
- describe.each(formDataCases)('Builds correct %p request', (mimeType, prototype, fixture) => {
450
- let body: URLSearchParams | FormData;
451
- let headers: Headers;
452
- beforeEach(async () => {
453
- const { getByRole } = render(<TryItWithPersistence httpOperation={fixture} />);
454
-
455
- // path param
456
- const nameField = getByRole('textbox', { name: 'name' }) as HTMLInputElement;
457
- userEvent.type(nameField, 'some-name');
458
-
459
- // click send
460
- clickSend();
461
-
462
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
463
- expect(fetchMock).toHaveBeenCalledTimes(1);
464
- body = fetchMock.mock.calls[0][1]!.body as URLSearchParams | FormData;
465
- headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
466
- expect(body).toBeInstanceOf(prototype);
467
- });
468
-
469
- it('Sets correct content type', () => {
470
- expect(headers.get('Content-Type')).toBe(mimeType === 'multipart/form-data' ? null : mimeType);
471
- });
472
-
473
- it('Sends user input', () => {
474
- expect(body.get('name')).toBe('some-name');
475
- });
476
-
477
- it('Includes untouched fields', () => {
478
- expect(body.get('completed')).toBe('');
479
- });
480
-
481
- it('Sets untouched required enums to their first value', () => {
482
- expect(body.get('someRequiredEnum')).toBe('a');
483
- });
484
- it('Does not set untouched optional enums', () => {
485
- expect(body.get('someOptionalEnum')).toBe('');
486
- });
487
- });
488
-
489
- describe('File Upload', () => {
490
- it('displays the name of the imported file in the string input', () => {
491
- render(<TryItWithPersistence httpOperation={multipartFormdataOperation} />);
492
-
493
- userEvent.upload(screen.getByLabelText('Upload'), new File(['something'], 'some-file'));
494
-
495
- expect(screen.getByLabelText('someFile')).toHaveValue('some-file');
496
- });
497
-
498
- it('allows to remove file after importing it', () => {
499
- render(<TryItWithPersistence httpOperation={multipartFormdataOperation} />);
500
-
501
- userEvent.upload(screen.getByLabelText('Upload'), new File(['something'], 'some-file'));
502
-
503
- userEvent.click(screen.getByLabelText('Remove file'));
504
-
505
- expect(screen.getByLabelText('someFile')).not.toHaveValue();
506
- });
507
-
508
- it('allows to upload file in multipart request', async () => {
509
- render(<TryItWithPersistence httpOperation={multipartFormdataOperation} />);
510
-
511
- userEvent.upload(screen.getByLabelText('Upload'), new File(['something'], 'some-file'));
512
-
513
- clickSend();
514
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
515
-
516
- const body = fetchMock.mock.calls[0][1]!.body as FormData;
517
-
518
- expect(body.get('someFile')).toBeInstanceOf(File);
519
- expect((body.get('someFile') as File).name).toBe('some-file');
520
- });
521
-
522
- it('allows to upload file in base64 format in multipart request', async () => {
523
- render(<TryItWithPersistence httpOperation={base64FileUpload} />);
524
-
525
- userEvent.upload(screen.getByLabelText('Upload'), new File(['something'], 'some-file'));
526
-
527
- clickSend();
528
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
529
- const body = fetchMock.mock.calls[0][1]!.body as FormData;
530
-
531
- // c29tZXRoaW5n is "something" encoded as base64
532
- expect(body.get('someFile')).toBe('c29tZXRoaW5n');
533
- });
534
- });
535
- });
536
-
537
- describe('Binary body', () => {
538
- it('shows panel when there is file input', () => {
539
- render(<TryItWithPersistence httpOperation={octetStreamOperation} />);
540
-
541
- let parametersHeader = screen.queryByText('Body');
542
- expect(parametersHeader).toBeInTheDocument();
543
- });
544
-
545
- it('displays file input correctly', () => {
546
- render(<TryItWithPersistence httpOperation={octetStreamOperation} />);
547
-
548
- const fileField = screen.getByRole('textbox', { name: 'file' }) as HTMLInputElement;
549
-
550
- expect(fileField.placeholder).toMatch(/pick a file/i);
551
- });
552
-
553
- it('builds correct application/octet-stream request and send file in the body', async () => {
554
- render(<TryItWithPersistence httpOperation={octetStreamOperation} />);
555
-
556
- userEvent.upload(screen.getByLabelText('Upload'), new File(['something'], 'some-file'));
557
-
558
- clickSend();
559
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
560
-
561
- const request = fetchMock.mock.calls[0];
562
- const requestBody = request[1]!.body as File;
563
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
564
-
565
- expect(requestBody).toBeInstanceOf(File);
566
- expect(requestBody.name).toBe('some-file');
567
- expect(headers.get('Content-Type')).toBe('application/octet-stream');
568
- });
569
-
570
- it('allows to send empty value', async () => {
571
- render(<TryItWithPersistence httpOperation={octetStreamOperation} />);
572
-
573
- clickSend();
574
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
575
-
576
- const body = fetchMock.mock.calls[0][1]!.body as FormData;
577
- expect(body).toBeUndefined();
578
- });
579
- });
580
-
581
- describe('Text Request Body', () => {
582
- describe('is attached', () => {
583
- it('to operation with PATCH method', async () => {
584
- render(<TryItWithPersistence httpOperation={patchWithRequestBody} />);
585
-
586
- clickSend();
587
-
588
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
589
- expect(fetchMock.mock.calls[0]![1]!.body).toEqual(expect.stringMatching(/{.*}/s));
590
- });
591
- });
592
-
593
- describe('is not attached', () => {
594
- it('to operation with HEAD method', async () => {
595
- render(<TryItWithPersistence httpOperation={headWithRequestBody} />);
596
-
597
- clickSend();
598
-
599
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
600
- expect(typeof fetchMock.mock.calls[0]![1]!.body).not.toBe('string');
601
- });
602
- });
603
-
604
- describe('when no request body examples', () => {
605
- it('hides panel when there is no schema for request body', () => {
606
- render(<TryItWithPersistence httpOperation={basicOperation} />);
607
-
608
- let bodyHeader = screen.queryByText('Body');
609
- expect(bodyHeader).not.toBeInTheDocument();
610
- });
611
-
612
- it('statically generates request body basing on request body schema', () => {
613
- render(<TryItWithPersistence httpOperation={requestBody} />);
614
-
615
- let bodyHeader = screen.queryByText('Body');
616
- expect(bodyHeader).toBeInTheDocument();
617
-
618
- expect(JSON.parse(screen.getByRole('textbox').textContent || '')).toEqual({ name: 'string', age: 0 });
619
- });
620
-
621
- it('does not generate request body from schema when schema is empty', () => {
622
- render(<TryItWithPersistence httpOperation={requestBodyEmptySchema} />);
623
-
624
- let bodyHeader = screen.queryByText('Body');
625
- expect(bodyHeader).toBeInTheDocument();
626
-
627
- expect(screen.getByRole('textbox')).toHaveTextContent('');
628
- });
629
- });
630
-
631
- describe('when there are request body examples', () => {
632
- let examplesItems = ['example-1', 'named example', 'example-3'];
633
-
634
- it("is populated to first example if there's one", () => {
635
- render(<TryItWithPersistence httpOperation={examplesRequestBody} />);
636
- expect(JSON.parse(screen.getByRole('textbox').textContent || '')).toEqual({
637
- name: 'Andrew',
638
- age: 19,
639
- trial: true,
640
- });
641
- });
642
-
643
- it('resets the textbox after httpOperation change', async () => {
644
- const { rerender } = render(<TryItWithPersistence httpOperation={examplesRequestBody} />);
645
- const textbox = screen.getByRole('textbox');
646
- userEvent.type(textbox, 'asd');
647
- rerender(<TryItWithPersistence httpOperation={requestBody} />);
648
- await waitFor(() =>
649
- expect(JSON.parse(screen.getByRole('textbox').textContent || '')).toEqual({
650
- name: 'string',
651
- age: 0,
652
- }),
653
- );
654
- });
655
-
656
- it('allows users to choose request body examples from spec using dropdown menu', () => {
657
- render(<TryItWithPersistence httpOperation={examplesRequestBody} />);
658
- let examplesButton = screen.getByRole('button', { name: 'Examples' });
659
- userEvent.click(examplesButton);
660
-
661
- let examples = screen.getAllByRole('menuitem').map(el => el.textContent);
662
- expect(examples).toEqual(examplesItems);
663
-
664
- userEvent.click(screen.getByRole('menuitem', { name: 'named example' }));
665
- expect(JSON.parse(screen.getByRole('textbox').textContent || '')).toEqual({
666
- name: 'Jane',
667
- age: 36,
668
- trial: false,
669
- });
670
- });
671
-
672
- it('restarts modified example in CodeEditor to initial value after choosing it again', () => {
673
- render(<TryItWithPersistence httpOperation={examplesRequestBody} />);
674
- let examplesButton = screen.getByRole('button', { name: 'Examples' });
675
-
676
- const bodyTextBox = screen.getByRole('textbox');
677
-
678
- userEvent.type(bodyTextBox, 'I broke the test. Oh noooo... :(');
679
- expect(bodyTextBox).toHaveTextContent('I broke the test. Oh noooo... :(');
680
-
681
- userEvent.click(examplesButton);
682
- userEvent.click(screen.getByRole('menuitem', { name: 'example-1' }));
683
- expect(JSON.parse(screen.getByRole('textbox').textContent || '')).toEqual({
684
- name: 'Andrew',
685
- age: 19,
686
- trial: true,
687
- });
688
- });
689
-
690
- it('sends a request with request body from example', async () => {
691
- const json = {
692
- name: 'Andrew',
693
- age: 19,
694
- trial: true,
695
- };
696
-
697
- render(<TryItWithPersistence httpOperation={examplesRequestBody} />);
698
-
699
- expect(JSON.parse(screen.getByRole('textbox').textContent || '')).toEqual(json);
700
-
701
- clickSend();
702
-
703
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
704
- expect(JSON.parse(fetchMock.mock.calls[0]![1]!.body as string)).toEqual(json);
705
- });
706
- });
707
-
708
- describe('when there is only one example provided', () => {
709
- it('displays that only example body', () => {
710
- render(<TryItWithPersistence httpOperation={singleExampleRequestBody} />);
711
- expect(JSON.parse(screen.getByRole('textbox').textContent || '')).toEqual({
712
- name: 'Andrew',
713
- age: 19,
714
- trial: true,
715
- });
716
- });
717
-
718
- it('does not display select to choose examples', () => {
719
- render(<TryItWithPersistence httpOperation={singleExampleRequestBody} />);
720
-
721
- let examplesButton = screen.queryByRole('button', { name: 'Examples' });
722
-
723
- expect(examplesButton).not.toBeInTheDocument();
724
- });
725
- });
726
- });
727
-
728
- describe('Mocking', () => {
729
- it('Shows mock button', () => {
730
- render(<TryItWithPersistence httpOperation={basicOperation} mockUrl="https://mock-todos.stoplight.io" />);
731
-
732
- const serversButton = screen.getByRole('button', { name: /server/i });
733
- userEvent.click(serversButton);
734
-
735
- expect(screen.getByRole('menuitemradio', { name: /mock server/i })).toBeInTheDocument();
736
- });
737
-
738
- it('Invokes request with mocked data', async () => {
739
- render(<TryItWithPersistence httpOperation={basicOperation} mockUrl="https://mock-todos.stoplight.io" />);
740
-
741
- let serversButton = screen.getByRole('button', { name: /server/i });
742
- userEvent.click(serversButton);
743
-
744
- // select mock server
745
- let enableItem = screen.getByRole('menuitemradio', { name: /mock server/i });
746
- userEvent.click(enableItem);
747
-
748
- // open mock dropdown
749
- const mockButton = screen.getByRole('button', { name: /mock settings/i });
750
- userEvent.click(mockButton);
751
-
752
- // set response code
753
- const responseCodeItem = await screen.getByRole('menuitemcheckbox', { name: '200' });
754
- expect(responseCodeItem).toBeInTheDocument();
755
- userEvent.click(responseCodeItem);
756
-
757
- // and send
758
- clickSend();
759
-
760
- await waitFor(() => expect(screen.getByRole('button', { name: /send/i })).toBeEnabled());
761
-
762
- await waitFor(() => expect(fetchMock).toHaveBeenCalledTimes(1));
763
-
764
- // select regular server and send
765
- userEvent.click(serversButton);
766
- let server1 = screen.getByRole('menuitemradio', { name: /live server/i });
767
- userEvent.click(server1);
768
-
769
- clickSend();
770
- await waitFor(() => expect(fetchMock).toHaveBeenCalledTimes(2));
771
-
772
- expect(fetchMock).toHaveBeenCalledTimes(2);
773
- expect(fetchMock.mock.calls).toEqual([
774
- [
775
- 'https://mock-todos.stoplight.io/todos',
776
- expect.objectContaining({
777
- method: 'GET',
778
- headers: {
779
- Prefer: 'code=200',
780
- },
781
- }),
782
- ],
783
- [
784
- 'https://todos.stoplight.io/todos',
785
- expect.objectContaining({
786
- method: 'GET',
787
- headers: {},
788
- }),
789
- ],
790
- ]);
791
- });
792
-
793
- it('Invokes request with no Prefer header if mock data is not selected', async () => {
794
- render(<TryItWithPersistence httpOperation={basicOperation} mockUrl="https://mock-todos.stoplight.io" />);
795
-
796
- let serversButton = screen.getByRole('button', { name: /server/i });
797
- userEvent.click(serversButton);
798
-
799
- // select mock server
800
- let enableItem = screen.getByRole('menuitemradio', { name: /mock server/i });
801
- userEvent.click(enableItem);
802
-
803
- clickSend();
804
-
805
- await waitFor(() => expect(screen.getByRole('button', { name: /send/i })).toBeEnabled());
806
-
807
- await waitFor(() => expect(fetchMock).toHaveBeenCalledTimes(1));
808
-
809
- expect(fetchMock.mock.calls).toEqual([
810
- [
811
- 'https://mock-todos.stoplight.io/todos',
812
- expect.objectContaining({
813
- method: 'GET',
814
- headers: {},
815
- }),
816
- ],
817
- ]);
818
- });
819
-
820
- it('Persists mocking options between operations', async () => {
821
- const { rerender } = render(
822
- <MosaicProvider>
823
- <PersistenceContextProvider>
824
- <TryIt httpOperation={putOperation} mockUrl="https://mock-todos.stoplight.io" />
825
- </PersistenceContextProvider>
826
- </MosaicProvider>,
827
- );
828
-
829
- let serversButton = screen.getByRole('button', { name: /server/i });
830
- userEvent.click(serversButton);
831
-
832
- // select mock server
833
- let enableItem = screen.getByRole('menuitemradio', { name: /mock server/i });
834
- userEvent.click(enableItem);
835
-
836
- // open mock dropdown
837
- const mockButton = screen.getByRole('button', { name: /mock settings/i });
838
- userEvent.click(mockButton);
839
-
840
- // set response code
841
- const responseCodeItem = await screen.getByRole('menuitemcheckbox', { name: '200' });
842
- expect(responseCodeItem).toBeInTheDocument();
843
- userEvent.click(responseCodeItem);
844
-
845
- // and send
846
- clickSend();
847
-
848
- // unmount (to make sure parameters are not simply stored in component state)
849
- rerender(
850
- <MosaicProvider>
851
- <PersistenceContextProvider>
852
- <div />
853
- </PersistenceContextProvider>
854
- </MosaicProvider>,
855
- );
856
-
857
- // mount a different instance
858
-
859
- rerender(
860
- <MosaicProvider>
861
- <PersistenceContextProvider>
862
- <TryIt httpOperation={basicOperation} mockUrl="https://mock-todos.stoplight.io" />
863
- </PersistenceContextProvider>
864
- </MosaicProvider>,
865
- );
866
-
867
- clickSend();
868
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
869
-
870
- expect(fetchMock).toBeCalledWith(
871
- 'https://mock-todos.stoplight.io/todos',
872
- expect.objectContaining({
873
- method: 'GET',
874
- headers: {
875
- Prefer: 'code=200',
876
- },
877
- }),
878
- );
879
- });
880
- });
881
-
882
- describe('Authentication', () => {
883
- describe('Panel', () => {
884
- it('is displayed if operation has a security', () => {
885
- render(<TryItWithPersistence httpOperation={putOperation} />);
886
-
887
- let authPanel = screen.getByText('Auth');
888
- expect(authPanel).toBeInTheDocument();
889
- });
890
-
891
- it('does not crash when operation security section is an empty array', () => {
892
- render(<TryItWithPersistence httpOperation={emptySecurityOperation} />);
893
-
894
- let authPanel = screen.queryByText('Auth');
895
- expect(authPanel).toBeInTheDocument();
896
-
897
- let noAuthCount = screen.getAllByText('No auth selected').length;
898
- expect(noAuthCount).toBe(1);
899
- });
900
-
901
- it("does not show up the Security Schemes select if there's only one schema", () => {
902
- render(<TryItWithPersistence httpOperation={singleSecurityOperation} />);
903
-
904
- let securitySchemesMenu = screen.queryByText('Security Schemes');
905
- expect(securitySchemesMenu).not.toBeInTheDocument();
906
- });
907
-
908
- it('allows to select a security schemes from dropdown menu', () => {
909
- render(<TryItWithPersistence httpOperation={putOperation} />);
910
-
911
- const securitySchemesButton = screen.getByLabelText('security-schemes');
912
- userEvent.click(securitySchemesButton);
913
-
914
- const securitySchemes = screen.getAllByRole('menuitemcheckbox', { name: 'OAuth 2.0' })[0];
915
- userEvent.click(securitySchemes);
916
-
917
- expect(securitySchemesButton).toHaveTextContent('OAuth 2.0');
918
- });
919
-
920
- it('preserves state when changing schemes', async () => {
921
- render(<TryItWithPersistence httpOperation={putOperation} />);
922
-
923
- let APIKeyField = screen.getByLabelText('API Key');
924
- userEvent.type(APIKeyField, '123');
925
-
926
- // switch to OAuth
927
- let securitySchemesButton = screen.getByLabelText('security-schemes');
928
- userEvent.click(securitySchemesButton);
929
-
930
- let securitySchemes = screen.getAllByRole('menuitemcheckbox', { name: 'OAuth 2.0' })[0];
931
- userEvent.click(securitySchemes);
932
-
933
- // switch back to API Key
934
- userEvent.click(securitySchemesButton);
935
-
936
- securitySchemes = screen.getAllByRole('menuitemcheckbox', { name: 'API Key (api_key)' })[0];
937
- userEvent.click(securitySchemes);
938
-
939
- APIKeyField = screen.getByLabelText('API Key');
940
- expect(APIKeyField).toHaveValue('123');
941
- });
942
-
943
- it('preserves the state when rerendering component', async () => {
944
- render(<TryItWithPersistence httpOperation={putOperation} />);
945
-
946
- let APIKeyField = screen.getByLabelText('API Key');
947
- userEvent.type(APIKeyField, '123');
948
-
949
- cleanup();
950
-
951
- render(<TryItWithPersistence httpOperation={putOperation} />);
952
-
953
- APIKeyField = screen.getByLabelText('API Key');
954
- expect(APIKeyField).toHaveValue('123');
955
- });
956
-
957
- it('invalidated unsupported security schemes between different operations', () => {
958
- const { rerender } = render(<TryItWithPersistence httpOperation={basicSecurityOperation} />);
959
-
960
- let usernameInput = screen.getByLabelText('Username');
961
- let passwordInput = screen.getByLabelText('Password');
962
-
963
- userEvent.type(usernameInput, 'user');
964
- userEvent.type(passwordInput, 'password');
965
-
966
- rerender(<TryItWithPersistence httpOperation={bearerSecurityOperation} />);
967
-
968
- const tokenInput = screen.getByLabelText('Token');
969
- userEvent.type(tokenInput, 'Bearer 1234');
970
-
971
- rerender(<TryItWithPersistence httpOperation={basicSecurityOperation} />);
972
-
973
- usernameInput = screen.getByLabelText('Username');
974
- passwordInput = screen.getByLabelText('Password');
975
-
976
- expect(usernameInput).toBeInTheDocument();
977
- expect(passwordInput).toBeInTheDocument();
978
- });
979
-
980
- it('keep security schemes between different operations', () => {
981
- const { rerender } = render(<TryItWithPersistence httpOperation={basicSecurityOperation} />);
982
-
983
- let usernameInput = screen.getByLabelText('Username');
984
- let passwordInput = screen.getByLabelText('Password');
985
-
986
- userEvent.type(usernameInput, 'user');
987
- userEvent.type(passwordInput, 'password');
988
-
989
- rerender(<TryItWithPersistence httpOperation={putOperation} />);
990
-
991
- usernameInput = screen.getByLabelText('Username');
992
- passwordInput = screen.getByLabelText('Password');
993
-
994
- expect(usernameInput).toHaveValue('user');
995
- expect(passwordInput).toHaveValue('password');
996
- });
997
-
998
- it('adds key value to menu items if multiple schemes of same security type', () => {
999
- render(<TryItWithPersistence httpOperation={putOperation} />);
1000
-
1001
- let securitySchemesButton = screen.getByLabelText('security-schemes');
1002
- userEvent.click(securitySchemesButton);
1003
-
1004
- let securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'API Key (api_key)' });
1005
- userEvent.click(securitySchemes);
1006
-
1007
- // switch back to API Key
1008
- userEvent.click(securitySchemesButton);
1009
-
1010
- securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'API Key (api_key2)' });
1011
- userEvent.click(securitySchemes);
1012
- });
1013
-
1014
- it('keeps distinct values for multiple schemes of same security type', () => {
1015
- render(<TryItWithPersistence httpOperation={putOperation} />);
1016
-
1017
- // Fill in 123 for API Key 1
1018
- let APIKeyField = screen.getByLabelText('API Key');
1019
- userEvent.type(APIKeyField, '123');
1020
-
1021
- // Fill in 456 for API Key 2
1022
- let securitySchemesButton = screen.getByLabelText('security-schemes');
1023
- userEvent.click(securitySchemesButton);
1024
- let securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'API Key (api_key2)' });
1025
- userEvent.click(securitySchemes);
1026
- APIKeyField = screen.getByLabelText('API Key 2');
1027
- userEvent.type(APIKeyField, '456');
1028
-
1029
- // switch back to API Key 1 confirm still 123
1030
- userEvent.click(securitySchemesButton);
1031
- securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'API Key (api_key)' });
1032
- userEvent.click(securitySchemes);
1033
- APIKeyField = screen.getByLabelText('API Key');
1034
- expect(APIKeyField).toHaveValue('123');
1035
-
1036
- // switch back to API Key 2 confirm still 456
1037
- userEvent.click(securitySchemesButton);
1038
- securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'API Key (api_key2)' });
1039
- userEvent.click(securitySchemes);
1040
- APIKeyField = screen.getByLabelText('API Key 2');
1041
- expect(APIKeyField).toHaveValue('456');
1042
- });
1043
-
1044
- it('renders AND security correctly in menu item list, retaining values through rerender', () => {
1045
- const { rerender } = render(<TryItWithPersistence httpOperation={putOperation} />);
1046
-
1047
- // Select AND security from menu
1048
- let securitySchemesButton = screen.getByLabelText('security-schemes');
1049
- userEvent.click(securitySchemesButton);
1050
- let securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'API Key & Basic Auth' });
1051
- userEvent.click(securitySchemes);
1052
-
1053
- // Fill in a value from each scheme
1054
- let APIKeyField = screen.getByLabelText('API Key 2');
1055
- userEvent.type(APIKeyField, '123');
1056
-
1057
- let usernameInput = screen.getByLabelText('Username');
1058
- userEvent.type(usernameInput, 'user');
1059
-
1060
- // Rerender and confirm values
1061
- rerender(<TryItWithPersistence httpOperation={putOperation} />);
1062
-
1063
- APIKeyField = screen.getByLabelText('API Key 2');
1064
- usernameInput = screen.getByLabelText('Username');
1065
-
1066
- expect(usernameInput).toHaveValue('user');
1067
- expect(APIKeyField).toHaveValue('123');
1068
- });
1069
-
1070
- it('renders None in the menu if a Optional security auth {} is presented', () => {
1071
- render(<TryItWithPersistence httpOperation={putOperation} />);
1072
-
1073
- let securitySchemesButton = screen.getByLabelText('security-schemes');
1074
- userEvent.click(securitySchemesButton);
1075
-
1076
- let securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'None' });
1077
- userEvent.click(securitySchemes);
1078
- });
1079
-
1080
- it('display No auth selected if user chooses None in the menu', () => {
1081
- render(<TryItWithPersistence httpOperation={putOperation} />);
1082
-
1083
- let securitySchemesButton = screen.getByLabelText('security-schemes');
1084
- userEvent.click(securitySchemesButton);
1085
-
1086
- let securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'OpenID Connect' });
1087
- userEvent.click(securitySchemes);
1088
- let noAuth = screen.queryByText('No auth selected');
1089
- expect(noAuth).toBe(null);
1090
-
1091
- userEvent.click(securitySchemesButton);
1092
- securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'None' });
1093
- userEvent.click(securitySchemes);
1094
- let noAuthCount = screen.getAllByText('No auth selected').length;
1095
- expect(noAuthCount).toBe(1);
1096
- });
1097
- });
1098
-
1099
- describe('API Key component', () => {
1100
- it('is displayed for security of that type', () => {
1101
- render(<TryItWithPersistence httpOperation={putOperation} />);
1102
-
1103
- const APIKeyName = screen.getByLabelText('API Key');
1104
- expect(APIKeyName).toBeInTheDocument();
1105
- });
1106
- it('removes duplicated parameters', () => {
1107
- render(<TryItWithPersistence httpOperation={duplicatedSecurityScheme} />);
1108
-
1109
- // check if query param with the same name as security is removed from OperationParameters (case insensitive)
1110
- const queryParam = screen.queryByLabelText('api-key');
1111
- expect(queryParam).not.toBeInTheDocument();
1112
-
1113
- // check if header with the same name as security is removed from OperationParameters (case insensitive)
1114
- const header = screen.queryByLabelText('Api-KeY');
1115
- expect(header).not.toBeInTheDocument();
1116
- });
1117
-
1118
- it('attaches auth token as a query parameter', async () => {
1119
- render(<TryItWithPersistence httpOperation={duplicatedSecurityScheme} />);
1120
-
1121
- const APIKeyField = screen.getByLabelText('API-Key');
1122
- userEvent.type(APIKeyField, '123');
1123
-
1124
- // click send
1125
- clickSend();
1126
-
1127
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1128
-
1129
- const url = new URL(fetchMock.mock.calls[0][0] as string);
1130
- const queryParams = url.searchParams;
1131
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
1132
-
1133
- // assert that query params are passed
1134
- expect(queryParams.get('API-Key')).toBe('123');
1135
-
1136
- // make sure we don't attach security duplicated in Operation Parameters
1137
- expect(queryParams.get('api-key')).toBeNull();
1138
- expect(headers.get('Api-KeY')).toBeNull();
1139
- });
1140
-
1141
- it('attaches auth token as a header', async () => {
1142
- render(<TryItWithPersistence httpOperation={singleSecurityOperation} />);
1143
-
1144
- const APIKeyField = screen.getByLabelText('API-Key');
1145
- userEvent.type(APIKeyField, '123');
1146
-
1147
- // click send
1148
- clickSend();
1149
-
1150
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1151
-
1152
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
1153
- expect(headers.get('API-Key')).toBe('123');
1154
- });
1155
- });
1156
-
1157
- describe('OAuth2 Component', () => {
1158
- it('allows to send a OAuth2 request', async () => {
1159
- render(<TryItWithPersistence httpOperation={putOperation} />);
1160
-
1161
- const securitySchemesButton = screen.getByLabelText('security-schemes');
1162
- userEvent.click(securitySchemesButton);
1163
-
1164
- const securitySchemes = screen.getAllByRole('menuitemcheckbox', { name: 'OAuth 2.0' })[0];
1165
- userEvent.click(securitySchemes);
1166
-
1167
- const tokenInput = screen.getByLabelText('Token');
1168
-
1169
- userEvent.type(tokenInput, 'Bearer 0a1b2c');
1170
-
1171
- const todoIdField = screen.getByLabelText('todoId');
1172
- userEvent.type(todoIdField, '123');
1173
-
1174
- clickSend();
1175
-
1176
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1177
-
1178
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
1179
- expect(headers.get('Authorization')).toBe('Bearer 0a1b2c');
1180
- });
1181
-
1182
- it('does not include header parameters conflicting with OAuth2 scheme', async () => {
1183
- render(<TryItWithPersistence httpOperation={duplicatedSecurityScheme} />);
1184
-
1185
- const header = screen.queryByLabelText('authorization');
1186
- expect(header).not.toBeInTheDocument();
1187
- });
1188
- });
1189
-
1190
- describe('Basic Auth Component', () => {
1191
- it('allows to send a Basic Auth request', async () => {
1192
- render(<TryItWithPersistence httpOperation={putOperation} />);
1193
-
1194
- const securitySchemesButton = screen.getByLabelText('security-schemes');
1195
- userEvent.click(securitySchemesButton);
1196
-
1197
- const securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'Basic Auth (basicKey)' });
1198
- userEvent.click(securitySchemes);
1199
-
1200
- const usernameInput = screen.getByLabelText('Username');
1201
- const passwordInput = screen.getByLabelText('Password');
1202
-
1203
- userEvent.type(usernameInput, 'user');
1204
- userEvent.type(passwordInput, 'password');
1205
-
1206
- const todoIdField = screen.getByLabelText('todoId');
1207
- userEvent.type(todoIdField, '123');
1208
-
1209
- clickSend();
1210
-
1211
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1212
-
1213
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
1214
- expect(headers.get('Authorization')).toBe('Basic dXNlcjpwYXNzd29yZA==');
1215
- });
1216
- });
1217
-
1218
- describe('Bearer Auth Component', () => {
1219
- it('allows to send a Bearer Auth request', async () => {
1220
- render(<TryItWithPersistence httpOperation={putOperation} />);
1221
-
1222
- const securitySchemesButton = screen.getByLabelText('security-schemes');
1223
- userEvent.click(securitySchemesButton);
1224
-
1225
- const securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'Bearer Auth (bearerKey)' });
1226
- userEvent.click(securitySchemes);
1227
-
1228
- const tokenInput = screen.getByLabelText('Token');
1229
-
1230
- userEvent.type(tokenInput, '0a1b2c');
1231
-
1232
- const todoIdField = screen.getByLabelText('todoId');
1233
- userEvent.type(todoIdField, '123');
1234
-
1235
- clickSend();
1236
-
1237
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1238
-
1239
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
1240
- expect(headers.get('Authorization')).toBe('Bearer 0a1b2c');
1241
- });
1242
- });
1243
-
1244
- describe('Digest Auth Component', () => {
1245
- it('allows to send a Digest Auth request', async () => {
1246
- render(<TryItWithPersistence httpOperation={putOperation} />);
1247
-
1248
- const securitySchemesButton = screen.getByLabelText('security-schemes');
1249
- userEvent.click(securitySchemesButton);
1250
-
1251
- const securitySchemes = screen.getByRole('menuitemcheckbox', { name: 'Digest Auth (digest)' });
1252
- userEvent.click(securitySchemes);
1253
-
1254
- const authInput = screen.getByLabelText('Authorization');
1255
-
1256
- const digestContent = `Digest username="Mufasa",
1257
- realm="testrealm@host.com",
1258
- nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",
1259
- uri="/dir/index.html",
1260
- qop=auth,
1261
- nc=00000001,
1262
- cnonce="0a4f113b",
1263
- response="6629fae49393a05397450978507c4ef1",
1264
- opaque="5ccc069c403ebaf9f0171e9517f40e41"
1265
- `;
1266
-
1267
- const expectedDigestContent = `Digest username="Mufasa", realm="testrealm@host.com", nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093", uri="/dir/index.html", qop=auth, nc=00000001, cnonce="0a4f113b", response="6629fae49393a05397450978507c4ef1", opaque="5ccc069c403ebaf9f0171e9517f40e41"`;
1268
-
1269
- userEvent.type(authInput, digestContent);
1270
-
1271
- const todoIdField = screen.getByLabelText('todoId');
1272
- userEvent.type(todoIdField, '123');
1273
-
1274
- clickSend();
1275
-
1276
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1277
-
1278
- const headers = new Headers(fetchMock.mock.calls[0][1]!.headers);
1279
- expect(headers.get('Authorization')).toBe(expectedDigestContent);
1280
- });
1281
- });
1282
- });
1283
-
1284
- describe('Ref resolving', () => {
1285
- it('generates sample body from refed parameter', async () => {
1286
- render(
1287
- <InlineRefResolverProvider document={referencedBody}>
1288
- <TryItWithPersistence httpOperation={referencedBody} />
1289
- </InlineRefResolverProvider>,
1290
- );
1291
-
1292
- clickSend();
1293
-
1294
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1295
- expect(JSON.parse(fetchMock.mock.calls[0]![1]!.body as string)).toEqual({ name: 'string', completed: true });
1296
- });
1297
- });
1298
-
1299
- describe('Multiple Servers', () => {
1300
- it('shows select if there is more than one server available', () => {
1301
- render(<TryItWithPersistence httpOperation={putOperation} />);
1302
-
1303
- const serversButton = screen.getByRole('button', { name: /server/i });
1304
-
1305
- expect(serversButton).toHaveTextContent('Server 1');
1306
- });
1307
-
1308
- it('allows to choose other server', async () => {
1309
- render(<TryItWithPersistence httpOperation={putOperation} />);
1310
-
1311
- const serversButton = screen.getByRole('button', { name: /server/i });
1312
- userEvent.click(serversButton);
1313
-
1314
- const enableItem = screen.getByRole('menuitemradio', { name: /development/i });
1315
- userEvent.click(enableItem);
1316
-
1317
- expect(serversButton).toHaveTextContent('Development');
1318
- });
1319
-
1320
- it('shows server variables', async () => {
1321
- render(<TryItWithPersistence httpOperation={putOperation} />);
1322
-
1323
- const serversButton = screen.getByRole('button', { name: /server/i });
1324
- userEvent.click(serversButton);
1325
-
1326
- const enableItem = screen.getByRole('menuitemradio', { name: /pr/i });
1327
- userEvent.click(enableItem);
1328
-
1329
- expect(serversButton).toHaveTextContent('PR');
1330
-
1331
- const protoField = screen.getByLabelText('proto');
1332
- expect(protoField).toBeInTheDocument();
1333
-
1334
- const prField = screen.getByLabelText('pr');
1335
- expect(prField).toBeInTheDocument();
1336
- });
1337
-
1338
- it('sends request to a chosen server url', async () => {
1339
- render(<TryItWithPersistence httpOperation={putOperation} />);
1340
-
1341
- const serversButton = screen.getByRole('button', { name: /server/i });
1342
- userEvent.click(serversButton);
1343
-
1344
- const enableItem = screen.getByRole('menuitemradio', { name: /development/i });
1345
- userEvent.click(enableItem);
1346
-
1347
- const todoIdField = screen.getByLabelText('todoId');
1348
- userEvent.type(todoIdField, '123');
1349
-
1350
- clickSend();
1351
-
1352
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1353
-
1354
- expect(fetchMock.mock.calls[0][0]).toContain('https://todos-dev.stoplight.io');
1355
- });
1356
-
1357
- it('sends a request using server variable default values', async () => {
1358
- render(<TryItWithPersistence httpOperation={putOperation} />);
1359
-
1360
- const serversButton = screen.getByRole('button', { name: /server/i });
1361
- userEvent.click(serversButton);
1362
-
1363
- const enableItem = screen.getByRole('menuitemradio', { name: /pr/i });
1364
- userEvent.click(enableItem);
1365
-
1366
- expect(serversButton).toHaveTextContent('PR');
1367
-
1368
- const todoIdField = screen.getByLabelText('todoId');
1369
- userEvent.type(todoIdField, '123');
1370
-
1371
- clickSend();
1372
-
1373
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1374
-
1375
- expect(fetchMock.mock.calls[0][0]).toContain('http://x-1000.todos-pr.stoplight.io');
1376
- });
1377
-
1378
- it('sends a request using server variable modified values', async () => {
1379
- render(<TryItWithPersistence httpOperation={putOperation} />);
1380
-
1381
- const serversButton = screen.getByRole('button', { name: /server/i });
1382
- userEvent.click(serversButton);
1383
-
1384
- const enableItem = screen.getByRole('menuitemradio', { name: /pr/i });
1385
- userEvent.click(enableItem);
1386
-
1387
- expect(serversButton).toHaveTextContent('PR');
1388
-
1389
- const todoIdField = screen.getByLabelText('todoId');
1390
- userEvent.type(todoIdField, '123');
1391
-
1392
- const prField = screen.getByLabelText('pr');
1393
- userEvent.type(prField, '123');
1394
-
1395
- const protoField = screen.getByLabelText('proto');
1396
- chooseOption(protoField, 'https');
1397
-
1398
- clickSend();
1399
-
1400
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1401
-
1402
- expect(fetchMock.mock.calls[0][0]).toContain('https://x-123.todos-pr.stoplight.io');
1403
- fetchMock.mockClear();
1404
-
1405
- userEvent.clear(prField);
1406
- clickSend();
1407
-
1408
- await waitFor(() => expect(fetchMock).toHaveBeenCalled());
1409
-
1410
- expect(fetchMock.mock.calls[0][0]).toContain('https://x-1000.todos-pr.stoplight.io');
1411
- });
1412
-
1413
- it('Persists chosen server between renders of different operations if URL is the same', async () => {
1414
- const operation1: IHttpOperation = {
1415
- ...basicOperation,
1416
- servers: [
1417
- { id: '?http-server-a?', description: 'op 1 server a', url: 'http://url-A.com' },
1418
- { id: '?http-server-b?', description: 'op 1 server b', url: 'http://url-B.com' },
1419
- { id: '?http-server-c?', description: 'op 1 server c', url: 'http://url-C.com' },
1420
- ],
1421
- };
1422
-
1423
- const operation2: IHttpOperation = {
1424
- ...basicOperation,
1425
- servers: [
1426
- { id: '?http-server-d?', description: 'op 2 server d', url: 'http://url-D.com' },
1427
- { id: '?http-server-e?', description: 'op 2 server e', url: 'http://url-E.com' },
1428
- { id: '?http-server-f?', description: 'op 2 server b', url: 'http://url-B.com' }, // same URL, should preserve this server
1429
- ],
1430
- };
1431
-
1432
- const { rerender } = render(
1433
- <MosaicProvider>
1434
- <PersistenceContextProvider>
1435
- <TryIt httpOperation={operation1} />
1436
- </PersistenceContextProvider>
1437
- </MosaicProvider>,
1438
- );
1439
-
1440
- let serversButton = screen.getByRole('button', { name: /server/i });
1441
- userEvent.click(serversButton);
1442
-
1443
- // select server b
1444
- let enableItem = screen.getByRole('menuitemradio', { name: /server b/i });
1445
- userEvent.click(enableItem);
1446
-
1447
- // unmount (to make sure parameters are not simply stored in component state)
1448
- rerender(
1449
- <MosaicProvider>
1450
- <PersistenceContextProvider>
1451
- <div />
1452
- </PersistenceContextProvider>
1453
- </MosaicProvider>,
1454
- );
1455
-
1456
- // mount a different instance
1457
-
1458
- rerender(
1459
- <MosaicProvider>
1460
- <PersistenceContextProvider>
1461
- <TryIt httpOperation={operation2} />
1462
- </PersistenceContextProvider>
1463
- </MosaicProvider>,
1464
- );
1465
-
1466
- // should still have server b selected since URLs match up
1467
- expect(screen.getByRole('button', { name: /server/i })).toHaveTextContent('op 2 server b');
1468
- });
1469
- });
1470
-
1471
- describe('Validation', () => {
1472
- it('does not show a warning message before sending the request', () => {
1473
- render(<TryItWithPersistence httpOperation={putOperation} />);
1474
-
1475
- expect(screen.queryByText("You didn't provide all of the required parameters!")).not.toBeInTheDocument();
1476
- });
1477
-
1478
- it('shows a warning message if at least one parameter is required but empty', () => {
1479
- render(<TryItWithPersistence httpOperation={putOperation} />);
1480
-
1481
- clickSend();
1482
-
1483
- expect(screen.queryByText("You didn't provide all of the required parameters!")).toBeInTheDocument();
1484
- });
1485
-
1486
- it('does not send a request if at least one parameter is required but empty', async () => {
1487
- render(<TryItWithPersistence httpOperation={putOperation} />);
1488
-
1489
- clickSend();
1490
-
1491
- // Fetching is called asynchronously, so I am waiting for it
1492
- // to be actually called. Without that the test always passes.
1493
- await Promise.resolve();
1494
-
1495
- expect(fetchMock).not.toHaveBeenCalled();
1496
- });
1497
-
1498
- it('does not show the message if required parameters are not empty', async () => {
1499
- render(<TryItWithPersistence httpOperation={putOperation} />);
1500
-
1501
- const todoIdField = screen.getByLabelText('todoId');
1502
- userEvent.type(todoIdField, '123');
1503
-
1504
- clickSend();
1505
-
1506
- await waitFor(() =>
1507
- expect(screen.queryByText("You didn't provide all of the required parameters!")).not.toBeInTheDocument(),
1508
- );
1509
- });
1510
- });
1511
- });