Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
24faa4690f | ||
|
|
7c33ae9c49 | ||
|
|
bf77474a11 | ||
|
|
8416b043ea | ||
|
|
0eb591b78a | ||
|
|
f53f92351e | ||
|
|
3fa3e2d89d | ||
|
|
a2015ee08b | ||
|
|
8fd919eede | ||
|
|
f1cdb6a032 | ||
|
|
a03c12786a | ||
|
|
a51bf1ea3e | ||
|
|
690e274e07 | ||
|
|
a2fee7ed58 | ||
|
|
90157c1a40 | ||
|
|
5ea2150ae7 | ||
|
|
d91e4e84b8 |
@@ -18,6 +18,10 @@
|
||||
"expose": "components",
|
||||
"src": "src/core/components"
|
||||
},
|
||||
{
|
||||
"expose": "containers",
|
||||
"src": "src/core/containers"
|
||||
},
|
||||
{
|
||||
"expose": "core",
|
||||
"src": "src/core"
|
||||
|
||||
@@ -11,15 +11,6 @@ branches:
|
||||
- master
|
||||
- /^v\d+\.\d+(\.\d+)?(-\S*)?$/
|
||||
install: "npm i && npm update"
|
||||
before_install:
|
||||
- | # quickly pass if only documentation is being updated
|
||||
if [ "$TRAVIS_PULL_REQUEST" != "false" ]; then
|
||||
TRAVIS_COMMIT_RANGE="FETCH_HEAD...$TRAVIS_BRANCH"
|
||||
git diff --name-only $TRAVIS_COMMIT_RANGE | grep -qvE '(\.md$)|(^(docs|examples))/' || {
|
||||
echo "Only docs were updated, stopping build process."
|
||||
exit
|
||||
}
|
||||
fi
|
||||
before_deploy:
|
||||
- npm run build
|
||||
env:
|
||||
|
||||
+1
-1
@@ -4,7 +4,7 @@ LABEL maintainer="fehguy"
|
||||
|
||||
ENV VERSION "v2.2.10"
|
||||
ENV FOLDER "swagger-ui-2.2.10"
|
||||
ENV API_URL "http://petstore.swagger.io/v2/swagger.json"
|
||||
ENV API_URL "https://petstore.swagger.io/v2/swagger.json"
|
||||
ENV API_URLS ""
|
||||
ENV API_KEY "**None**"
|
||||
ENV OAUTH_CLIENT_ID "**None**"
|
||||
|
||||
@@ -2,27 +2,25 @@
|
||||
|
||||
[](http://badge.fury.io/js/swagger-ui)
|
||||
|
||||
## New!
|
||||
|
||||
**This is the new version of swagger-ui, 3.x. Want to learn more? Check out our [FAQ](http://swagger.io/new-ui-faq/).**
|
||||
|
||||
**👉🏼 Want to score an easy open-source contribution?** Check out our [Good first issue](https://github.com/swagger-api/swagger-ui/issues?q=is%3Aissue+is%3Aopen+label%3A%22Good+first+issue%22) label.
|
||||
|
||||
As a brand new version, written from the ground up, there are some known issues and unimplemented features. Check out the [Known Issues](#known-issues) section for more details.
|
||||
**🕰️ Looking for the older version of Swagger UI?** Refer to the [*2.x* branch](https://github.com/swagger-api/swagger-ui/tree/2.x).
|
||||
|
||||
|
||||
This repository publishes to two different NPM modules:
|
||||
|
||||
* [swagger-ui](https://www.npmjs.com/package/swagger-ui) is a traditional npm module intended for use in JavaScript web application projects that are capable of resolving dependencies (via Webpack, Browserify, etc).
|
||||
* [swagger-ui-dist](https://www.npmjs.com/package/swagger-ui-dist) is a dependency-free module that includes everything you need to serve Swagger-UI in a server-side project, or a web project that can't resolve npm module dependencies.
|
||||
* [swagger-ui](https://www.npmjs.com/package/swagger-ui) is a traditional npm module intended for use in single-page applications that are capable of resolving dependencies (via Webpack, Browserify, etc).
|
||||
* [swagger-ui-dist](https://www.npmjs.com/package/swagger-ui-dist) is a dependency-free module that includes everything you need to serve Swagger-UI in a server-side project, or a single-page application that can't resolve npm module dependencies.
|
||||
|
||||
We strongly suggest that you use `swagger-ui` instead of `swagger-ui-dist` if you're building a single-page application, since `swagger-ui-dist` is significantly larger.
|
||||
|
||||
For the older version of swagger-ui, refer to the [*2.x branch*](https://github.com/swagger-api/swagger-ui/tree/2.x).
|
||||
|
||||
## Compatibility
|
||||
The OpenAPI Specification has undergone 5 revisions since initial creation in 2010. Compatibility between swagger-ui and the OpenAPI Specification is as follows:
|
||||
The OpenAPI Specification has undergone 5 revisions since initial creation in 2010. Compatibility between Swagger UI and the OpenAPI Specification is as follows:
|
||||
|
||||
Swagger UI Version | Release Date | OpenAPI Spec compatibility | Notes
|
||||
------------------ | ------------ | -------------------------- | -----
|
||||
3.16.0 | 2018-05-26 | 2.0, 3.0 | [tag v3.16.0](https://github.com/swagger-api/swagger-ui/tree/v3.16.0)
|
||||
3.17.1 | 2018-06-16 | 2.0, 3.0 | [tag v3.17.1](https://github.com/swagger-api/swagger-ui/tree/v3.17.1)
|
||||
3.0.21 | 2017-07-26 | 2.0 | [tag v3.0.21](https://github.com/swagger-api/swagger-ui/tree/v3.0.21)
|
||||
2.2.10 | 2017-01-04 | 1.1, 1.2, 2.0 | [tag v2.2.10](https://github.com/swagger-api/swagger-ui/tree/v2.2.10)
|
||||
2.1.5 | 2016-07-20 | 1.1, 1.2, 2.0 | [tag v2.1.5](https://github.com/swagger-api/swagger-ui/tree/v2.1.5)
|
||||
@@ -76,7 +74,7 @@ Please disclose any security-related issues or vulnerabilities by emailing [secu
|
||||
|
||||
## License
|
||||
|
||||
Copyright 2017 SmartBear Software
|
||||
Copyright 2018 SmartBear Software
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
|
||||
@@ -43,7 +43,7 @@
|
||||
window["SwaggerUIStandalonePreset"] = window["swagger-ui-standalone-preset"]
|
||||
// Build a system
|
||||
const ui = SwaggerUIBundle({
|
||||
url: "http://petstore.swagger.io/v2/swagger.json",
|
||||
url: "https://petstore.swagger.io/v2/swagger.json",
|
||||
dom_id: '#swagger-ui',
|
||||
presets: [
|
||||
SwaggerUIBundle.presets.apis,
|
||||
|
||||
Vendored
+1
-1
@@ -41,7 +41,7 @@
|
||||
|
||||
// Build a system
|
||||
const ui = SwaggerUIBundle({
|
||||
url: "http://petstore.swagger.io/v2/swagger.json",
|
||||
url: "https://petstore.swagger.io/v2/swagger.json",
|
||||
dom_id: '#swagger-ui',
|
||||
deepLinking: true,
|
||||
presets: [
|
||||
|
||||
Vendored
+48
-48
File diff suppressed because one or more lines are too long
Vendored
+1
-1
File diff suppressed because one or more lines are too long
Vendored
+3
-3
File diff suppressed because one or more lines are too long
+1
-1
File diff suppressed because one or more lines are too long
Vendored
+1
-1
File diff suppressed because one or more lines are too long
Vendored
+2
-2
File diff suppressed because one or more lines are too long
Vendored
+1
-1
File diff suppressed because one or more lines are too long
+4
-4
@@ -38,10 +38,10 @@ fi
|
||||
if [[ -f $SWAGGER_JSON ]]; then
|
||||
cp -s $SWAGGER_JSON $NGINX_ROOT
|
||||
REL_PATH="./$(basename $SWAGGER_JSON)"
|
||||
sed -i "s|http://petstore.swagger.io/v2/swagger.json|$REL_PATH|g" $INDEX_FILE
|
||||
sed -i "s|https://petstore.swagger.io/v2/swagger.json|$REL_PATH|g" $INDEX_FILE
|
||||
sed -i "s|http://example.com/api|$REL_PATH|g" $INDEX_FILE
|
||||
else
|
||||
sed -i "s|http://petstore.swagger.io/v2/swagger.json|$API_URL|g" $INDEX_FILE
|
||||
sed -i "s|https://petstore.swagger.io/v2/swagger.json|$API_URL|g" $INDEX_FILE
|
||||
sed -i "s|http://example.com/api|$API_URL|g" $INDEX_FILE
|
||||
fi
|
||||
|
||||
@@ -55,11 +55,11 @@ fi
|
||||
|
||||
# replace `url` with `urls` option if API_URLS is set
|
||||
if [[ -n "$API_URLS" ]]; then
|
||||
sed -i "s|url: .*,|urls: $API_URLS,|g" $INDEX_FILE
|
||||
sed -i "s|^\(\s*\)url: .*,|\1urls: $API_URLS,|g" $INDEX_FILE
|
||||
fi
|
||||
|
||||
# replace the PORT that nginx listens on if PORT is supplied
|
||||
if [[ -n "${PORT}" ]]; then
|
||||
if [[ -n "${PORT}" ]]; then
|
||||
sed -i "s|8080|${PORT}|g" /etc/nginx/nginx.conf
|
||||
fi
|
||||
|
||||
|
||||
@@ -40,7 +40,7 @@ const OperationsLayoutPlugin = () => {
|
||||
// Provide the plugin to Swagger-UI, and select OperationsLayout
|
||||
// as the layout for Swagger-UI
|
||||
SwaggerUI({
|
||||
url: "http://petstore.swagger.io/v2/swagger.json",
|
||||
url: "https://petstore.swagger.io/v2/swagger.json",
|
||||
plugins: [ OperationsLayoutPlugin ],
|
||||
layout: "OperationsLayout"
|
||||
})
|
||||
@@ -85,7 +85,7 @@ const AugmentingLayoutPlugin = () => {
|
||||
// Provide the plugin to Swagger-UI, and select AugmentingLayout
|
||||
// as the layout for Swagger-UI
|
||||
SwaggerUI({
|
||||
url: "http://petstore.swagger.io/v2/swagger.json",
|
||||
url: "https://petstore.swagger.io/v2/swagger.json",
|
||||
plugins: [ AugmentingLayoutPlugin ],
|
||||
layout: "AugmentingLayout"
|
||||
})
|
||||
|
||||
@@ -17,7 +17,7 @@ Script name | Description
|
||||
--- | ---
|
||||
`build` | Build a new set of JS and CSS assets, and output them to `/dist`.
|
||||
`build-bundle` | Build `swagger-ui-bundle.js` only.
|
||||
`build-core` | Build `swagger-ui.(js|css)` only.
|
||||
`build-core` | Build `swagger-ui.(js\|css)` only.
|
||||
`build-standalone` | Build `swagger-ui-standalone-preset.js` only.
|
||||
|
||||
### Testing
|
||||
|
||||
+1
-1
@@ -21,7 +21,7 @@ You can verify CORS support with one of three techniques:
|
||||
- Curl your API and inspect the headers. For instance:
|
||||
|
||||
```bash
|
||||
$ curl -I "http://petstore.swagger.io/v2/swagger.json"
|
||||
$ curl -I "https://petstore.swagger.io/v2/swagger.json"
|
||||
HTTP/1.1 200 OK
|
||||
Date: Sat, 31 Jan 2015 23:05:44 GMT
|
||||
Access-Control-Allow-Origin: *
|
||||
|
||||
@@ -44,7 +44,7 @@ you could do something like this:
|
||||
var SwaggerUIBundle = require('swagger-ui-dist').SwaggerUIBundle
|
||||
|
||||
const ui = SwaggerUIBundle({
|
||||
url: "http://petstore.swagger.io/v2/swagger.json",
|
||||
url: "https://petstore.swagger.io/v2/swagger.json",
|
||||
dom_id: '#swagger-ui',
|
||||
presets: [
|
||||
SwaggerUIBundle.presets.apis,
|
||||
|
||||
+1
-1
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "swagger-ui",
|
||||
"version": "3.16.0",
|
||||
"version": "3.17.1",
|
||||
"main": "dist/swagger-ui.js",
|
||||
"repository": "git@github.com:swagger-api/swagger-ui.git",
|
||||
"contributors": [
|
||||
|
||||
@@ -6,63 +6,35 @@ export default class BaseLayout extends React.Component {
|
||||
static propTypes = {
|
||||
errSelectors: PropTypes.object.isRequired,
|
||||
errActions: PropTypes.object.isRequired,
|
||||
specActions: PropTypes.object.isRequired,
|
||||
specSelectors: PropTypes.object.isRequired,
|
||||
oas3Selectors: PropTypes.object.isRequired,
|
||||
oas3Actions: PropTypes.object.isRequired,
|
||||
layoutSelectors: PropTypes.object.isRequired,
|
||||
layoutActions: PropTypes.object.isRequired,
|
||||
getComponent: PropTypes.func.isRequired
|
||||
}
|
||||
|
||||
onFilterChange =(e) => {
|
||||
let {target: {value}} = e
|
||||
this.props.layoutActions.updateFilter(value)
|
||||
}
|
||||
|
||||
render() {
|
||||
let {
|
||||
specSelectors,
|
||||
specActions,
|
||||
getComponent,
|
||||
layoutSelectors,
|
||||
oas3Selectors,
|
||||
oas3Actions
|
||||
} = this.props
|
||||
|
||||
let info = specSelectors.info()
|
||||
let url = specSelectors.url()
|
||||
let basePath = specSelectors.basePath()
|
||||
let host = specSelectors.host()
|
||||
let securityDefinitions = specSelectors.securityDefinitions()
|
||||
let externalDocs = specSelectors.externalDocs()
|
||||
let schemes = specSelectors.schemes()
|
||||
let servers = specSelectors.servers()
|
||||
let {specSelectors, getComponent} = this.props
|
||||
|
||||
let SvgAssets = getComponent("SvgAssets")
|
||||
let Info = getComponent("info")
|
||||
let InfoContainer = getComponent("InfoContainer", true)
|
||||
let VersionPragmaFilter = getComponent("VersionPragmaFilter")
|
||||
let Operations = getComponent("operations", true)
|
||||
let Models = getComponent("Models", true)
|
||||
let AuthorizeBtn = getComponent("authorizeBtn", true)
|
||||
let Row = getComponent("Row")
|
||||
let Col = getComponent("Col")
|
||||
let Servers = getComponent("Servers")
|
||||
let ServersContainer = getComponent("ServersContainer", true)
|
||||
let Errors = getComponent("errors", true)
|
||||
|
||||
let isLoading = specSelectors.loadingStatus() === "loading"
|
||||
let isFailed = specSelectors.loadingStatus() === "failed"
|
||||
let filter = layoutSelectors.currentFilter()
|
||||
|
||||
let inputStyle = {}
|
||||
if(isFailed) inputStyle.color = "red"
|
||||
if(isLoading) inputStyle.color = "#aaa"
|
||||
|
||||
const Schemes = getComponent("schemes")
|
||||
const SchemesContainer = getComponent("SchemesContainer", true)
|
||||
const FilterContainer = getComponent("FilterContainer", true)
|
||||
let isSwagger2 = specSelectors.isSwagger2()
|
||||
let isOAS3 = specSelectors.isOAS3()
|
||||
|
||||
const isSpecEmpty = !specSelectors.specStr()
|
||||
|
||||
if(isSpecEmpty) {
|
||||
let loadingMessage
|
||||
let isLoading = specSelectors.loadingStatus() === "loading"
|
||||
if(isLoading) {
|
||||
loadingMessage = <div className="loading"></div>
|
||||
} else {
|
||||
@@ -80,57 +52,19 @@ export default class BaseLayout extends React.Component {
|
||||
|
||||
<div className='swagger-ui'>
|
||||
<SvgAssets />
|
||||
<div>
|
||||
<VersionPragmaFilter isSwagger2={isSwagger2} isOAS3={isOAS3} alsoShow={<Errors/>}>
|
||||
<Errors/>
|
||||
<Row className="information-container">
|
||||
<Col mobile={12}>
|
||||
{ info.count() ? (
|
||||
<Info info={ info } url={ url } host={ host } basePath={ basePath } externalDocs={externalDocs} getComponent={getComponent}/>
|
||||
) : null }
|
||||
<InfoContainer/>
|
||||
</Col>
|
||||
</Row>
|
||||
{ schemes && schemes.size || securityDefinitions ? (
|
||||
<div className="scheme-container">
|
||||
<Col className="schemes wrapper" mobile={12}>
|
||||
{ schemes && schemes.size ? (
|
||||
<Schemes
|
||||
currentScheme={specSelectors.operationScheme()}
|
||||
schemes={ schemes }
|
||||
specActions={ specActions } />
|
||||
) : null }
|
||||
|
||||
{ securityDefinitions ? (
|
||||
<AuthorizeBtn />
|
||||
) : null }
|
||||
</Col>
|
||||
</div>
|
||||
) : null }
|
||||
<SchemesContainer/>
|
||||
|
||||
{ servers && servers.size ? (
|
||||
<div className="global-server-container">
|
||||
<Col className="servers wrapper" mobile={12}>
|
||||
<span className="servers-title">Server</span>
|
||||
<Servers
|
||||
servers={servers}
|
||||
currentServer={oas3Selectors.selectedServer()}
|
||||
setSelectedServer={oas3Actions.setSelectedServer}
|
||||
setServerVariableValue={oas3Actions.setServerVariableValue}
|
||||
getServerVariable={oas3Selectors.serverVariableValue}
|
||||
getEffectiveServerValue={oas3Selectors.serverEffectiveValue}
|
||||
/>
|
||||
</Col>
|
||||
</div>
|
||||
<ServersContainer/>
|
||||
|
||||
) : null}
|
||||
|
||||
{
|
||||
filter === null || filter === false ? null :
|
||||
<div className="filter-container">
|
||||
<Col className="filter wrapper" mobile={12}>
|
||||
<input className="operation-filter-input" placeholder="Filter by tag" type="text" onChange={this.onFilterChange} value={filter === true || filter === "true" ? "" : filter} disabled={isLoading} style={inputStyle} />
|
||||
</Col>
|
||||
</div>
|
||||
}
|
||||
<FilterContainer/>
|
||||
|
||||
<Row>
|
||||
<Col mobile={12} desktop={12} >
|
||||
@@ -142,7 +76,7 @@ export default class BaseLayout extends React.Component {
|
||||
<Models/>
|
||||
</Col>
|
||||
</Row>
|
||||
</div>
|
||||
</VersionPragmaFilter>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
@@ -0,0 +1,108 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
import ImPropTypes from "react-immutable-proptypes"
|
||||
import Im from "immutable"
|
||||
import { createDeepLinkPath, sanitizeUrl } from "core/utils"
|
||||
|
||||
export default class OperationTag extends React.Component {
|
||||
|
||||
static defaultProps = {
|
||||
tagObj: Im.fromJS({}),
|
||||
tag: "",
|
||||
}
|
||||
|
||||
static propTypes = {
|
||||
tagObj: ImPropTypes.map.isRequired,
|
||||
tag: PropTypes.string.isRequired,
|
||||
|
||||
layoutSelectors: PropTypes.object.isRequired,
|
||||
layoutActions: PropTypes.object.isRequired,
|
||||
|
||||
getConfigs: PropTypes.func.isRequired,
|
||||
getComponent: PropTypes.func.isRequired,
|
||||
|
||||
children: PropTypes.element,
|
||||
}
|
||||
|
||||
render() {
|
||||
const {
|
||||
tagObj,
|
||||
tag,
|
||||
children,
|
||||
|
||||
layoutSelectors,
|
||||
layoutActions,
|
||||
getConfigs,
|
||||
getComponent,
|
||||
} = this.props
|
||||
|
||||
let {
|
||||
docExpansion,
|
||||
deepLinking,
|
||||
} = getConfigs()
|
||||
|
||||
const isDeepLinkingEnabled = deepLinking && deepLinking !== "false"
|
||||
|
||||
const Collapse = getComponent("Collapse")
|
||||
const Markdown = getComponent("Markdown")
|
||||
const DeepLink = getComponent("DeepLink")
|
||||
|
||||
let tagDescription = tagObj.getIn(["tagDetails", "description"], null)
|
||||
let tagExternalDocsDescription = tagObj.getIn(["tagDetails", "externalDocs", "description"])
|
||||
let tagExternalDocsUrl = tagObj.getIn(["tagDetails", "externalDocs", "url"])
|
||||
|
||||
let isShownKey = ["operations-tag", createDeepLinkPath(tag)]
|
||||
let showTag = layoutSelectors.isShown(isShownKey, docExpansion === "full" || docExpansion === "list")
|
||||
|
||||
return (
|
||||
<div className={showTag ? "opblock-tag-section is-open" : "opblock-tag-section"} >
|
||||
|
||||
<h4
|
||||
onClick={() => layoutActions.show(isShownKey, !showTag)}
|
||||
className={!tagDescription ? "opblock-tag no-desc" : "opblock-tag" }
|
||||
id={isShownKey.join("-")}>
|
||||
<DeepLink
|
||||
enabled={isDeepLinkingEnabled}
|
||||
isShown={showTag}
|
||||
path={tag}
|
||||
text={tag} />
|
||||
{ !tagDescription ? <small></small> :
|
||||
<small>
|
||||
<Markdown source={tagDescription} />
|
||||
</small>
|
||||
}
|
||||
|
||||
<div>
|
||||
{ !tagExternalDocsDescription ? null :
|
||||
<small>
|
||||
{ tagExternalDocsDescription }
|
||||
{ tagExternalDocsUrl ? ": " : null }
|
||||
{ tagExternalDocsUrl ?
|
||||
<a
|
||||
href={sanitizeUrl(tagExternalDocsUrl)}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
target={"_blank"}
|
||||
>{tagExternalDocsUrl}</a> : null
|
||||
}
|
||||
</small>
|
||||
}
|
||||
</div>
|
||||
|
||||
<button
|
||||
className="expand-operation"
|
||||
title={showTag ? "Collapse operation": "Expand operation"}
|
||||
onClick={() => layoutActions.show(isShownKey, !showTag)}>
|
||||
|
||||
<svg className="arrow" width="20" height="20">
|
||||
<use href={showTag ? "#large-arrow-down" : "#large-arrow"} xlinkHref={showTag ? "#large-arrow-down" : "#large-arrow"} />
|
||||
</svg>
|
||||
</button>
|
||||
</h4>
|
||||
|
||||
<Collapse isOpened={showTag}>
|
||||
{children}
|
||||
</Collapse>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -1,7 +1,6 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
import Im from "immutable"
|
||||
import { createDeepLinkPath, sanitizeUrl } from "core/utils"
|
||||
|
||||
const SWAGGER2_OPERATION_METHODS = [
|
||||
"get", "put", "post", "delete", "options", "head", "patch"
|
||||
@@ -38,18 +37,12 @@ export default class Operations extends React.Component {
|
||||
let taggedOps = specSelectors.taggedOperations()
|
||||
|
||||
const OperationContainer = getComponent("OperationContainer", true)
|
||||
const Collapse = getComponent("Collapse")
|
||||
const Markdown = getComponent("Markdown")
|
||||
const DeepLink = getComponent("DeepLink")
|
||||
const OperationTag = getComponent("OperationTag")
|
||||
|
||||
let {
|
||||
docExpansion,
|
||||
maxDisplayedTags,
|
||||
deepLinking
|
||||
} = getConfigs()
|
||||
|
||||
const isDeepLinkingEnabled = deepLinking && deepLinking !== "false"
|
||||
|
||||
let filter = layoutSelectors.currentFilter()
|
||||
|
||||
if (filter) {
|
||||
@@ -66,88 +59,49 @@ export default class Operations extends React.Component {
|
||||
<div>
|
||||
{
|
||||
taggedOps.map( (tagObj, tag) => {
|
||||
let operations = tagObj.get("operations")
|
||||
let tagDescription = tagObj.getIn(["tagDetails", "description"], null)
|
||||
let tagExternalDocsDescription = tagObj.getIn(["tagDetails", "externalDocs", "description"])
|
||||
let tagExternalDocsUrl = tagObj.getIn(["tagDetails", "externalDocs", "url"])
|
||||
|
||||
let isShownKey = ["operations-tag", createDeepLinkPath(tag)]
|
||||
let showTag = layoutSelectors.isShown(isShownKey, docExpansion === "full" || docExpansion === "list")
|
||||
|
||||
const operations = tagObj.get("operations")
|
||||
return (
|
||||
<div className={showTag ? "opblock-tag-section is-open" : "opblock-tag-section"} key={"operation-" + tag}>
|
||||
|
||||
<h4
|
||||
onClick={() => layoutActions.show(isShownKey, !showTag)}
|
||||
className={!tagDescription ? "opblock-tag no-desc" : "opblock-tag" }
|
||||
id={isShownKey.join("-")}>
|
||||
<DeepLink
|
||||
enabled={isDeepLinkingEnabled}
|
||||
isShown={showTag}
|
||||
path={tag}
|
||||
text={tag} />
|
||||
{ !tagDescription ? <small></small> :
|
||||
<small>
|
||||
<Markdown source={tagDescription} />
|
||||
</small>
|
||||
}
|
||||
|
||||
<div>
|
||||
{ !tagExternalDocsDescription ? null :
|
||||
<small>
|
||||
{ tagExternalDocsDescription }
|
||||
{ tagExternalDocsUrl ? ": " : null }
|
||||
{ tagExternalDocsUrl ?
|
||||
<a
|
||||
href={sanitizeUrl(tagExternalDocsUrl)}
|
||||
onClick={(e) => e.stopPropagation()}
|
||||
target={"_blank"}
|
||||
>{tagExternalDocsUrl}</a> : null
|
||||
}
|
||||
</small>
|
||||
}
|
||||
</div>
|
||||
|
||||
<button className="expand-operation" title={showTag ? "Collapse operation": "Expand operation"} onClick={() => layoutActions.show(isShownKey, !showTag)}>
|
||||
<svg className="arrow" width="20" height="20">
|
||||
<use href={showTag ? "#large-arrow-down" : "#large-arrow"} xlinkHref={showTag ? "#large-arrow-down" : "#large-arrow"} />
|
||||
</svg>
|
||||
</button>
|
||||
</h4>
|
||||
|
||||
<Collapse isOpened={showTag}>
|
||||
{
|
||||
operations.map( op => {
|
||||
const path = op.get("path")
|
||||
const method = op.get("method")
|
||||
const specPath = Im.List(["paths", path, method])
|
||||
<OperationTag
|
||||
key={"operation-" + tag}
|
||||
tagObj={tagObj}
|
||||
tag={tag}
|
||||
layoutSelectors={layoutSelectors}
|
||||
layoutActions={layoutActions}
|
||||
getConfigs={getConfigs}
|
||||
getComponent={getComponent}>
|
||||
{
|
||||
operations.map( op => {
|
||||
const path = op.get("path")
|
||||
const method = op.get("method")
|
||||
const specPath = Im.List(["paths", path, method])
|
||||
|
||||
|
||||
// FIXME: (someday) this logic should probably be in a selector,
|
||||
// but doing so would require further opening up
|
||||
// selectors to the plugin system, to allow for dynamic
|
||||
// overriding of low-level selectors that other selectors
|
||||
// rely on. --KS, 12/17
|
||||
const validMethods = specSelectors.isOAS3() ?
|
||||
OAS3_OPERATION_METHODS : SWAGGER2_OPERATION_METHODS
|
||||
// FIXME: (someday) this logic should probably be in a selector,
|
||||
// but doing so would require further opening up
|
||||
// selectors to the plugin system, to allow for dynamic
|
||||
// overriding of low-level selectors that other selectors
|
||||
// rely on. --KS, 12/17
|
||||
const validMethods = specSelectors.isOAS3() ?
|
||||
OAS3_OPERATION_METHODS : SWAGGER2_OPERATION_METHODS
|
||||
|
||||
if(validMethods.indexOf(method) === -1) {
|
||||
return null
|
||||
}
|
||||
if(validMethods.indexOf(method) === -1) {
|
||||
return null
|
||||
}
|
||||
|
||||
return <OperationContainer
|
||||
key={`${path}-${method}`}
|
||||
specPath={specPath}
|
||||
op={op}
|
||||
path={path}
|
||||
method={method}
|
||||
tag={tag}
|
||||
/>
|
||||
}).toArray()
|
||||
}
|
||||
</Collapse>
|
||||
</div>
|
||||
)
|
||||
return <OperationContainer
|
||||
key={`${path}-${method}`}
|
||||
specPath={specPath}
|
||||
op={op}
|
||||
path={path}
|
||||
method={method}
|
||||
tag={tag}
|
||||
/>
|
||||
}).toArray()
|
||||
}
|
||||
|
||||
|
||||
</OperationTag>
|
||||
)
|
||||
}).toArray()
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,54 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
|
||||
export default class VersionPragmaFilter extends React.PureComponent {
|
||||
static propTypes = {
|
||||
isSwagger2: PropTypes.bool.isRequired,
|
||||
isOAS3: PropTypes.bool.isRequired,
|
||||
bypass: PropTypes.bool,
|
||||
alsoShow: PropTypes.element,
|
||||
children: PropTypes.any,
|
||||
}
|
||||
|
||||
static defaultProps = {
|
||||
alsoShow: null,
|
||||
children: null,
|
||||
bypass: false,
|
||||
}
|
||||
|
||||
render() {
|
||||
const { bypass, isSwagger2, isOAS3, alsoShow } = this.props
|
||||
|
||||
if(bypass) {
|
||||
return <div>{ this.props.children }</div>
|
||||
}
|
||||
|
||||
if(isSwagger2 && isOAS3) {
|
||||
return <div className="version-pragma">
|
||||
{alsoShow}
|
||||
<div className="version-pragma__message version-pragma__message--ambiguous">
|
||||
<div>
|
||||
<h3>Unable to render this definition</h3>
|
||||
<p><code>swagger</code> and <code>openapi</code> fields cannot be present in the same Swagger or OpenAPI definition. Please remove one of the fields.</p>
|
||||
<p>Supported version fields are <code>swagger: {"\"2.0\""}</code> and those that match <code>openapi: 3.0.n</code> (for example, <code>openapi: 3.0.0</code>).</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
}
|
||||
|
||||
if(!isSwagger2 && !isOAS3) {
|
||||
return <div className="version-pragma">
|
||||
{alsoShow}
|
||||
<div className="version-pragma__message version-pragma__message--missing">
|
||||
<div>
|
||||
<h3>Unable to render this definition</h3>
|
||||
<p>The provided definition does not specify a valid version field.</p>
|
||||
<p>Please indicate a valid Swagger or OpenAPI version field. Supported version fields are <code>swagger: {"\"2.0\""}</code> and those that match <code>openapi: 3.0.n</code> (for example, <code>openapi: 3.0.0</code>).</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
}
|
||||
|
||||
return <div>{ this.props.children }</div>
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
|
||||
export default class FilterContainer extends React.Component {
|
||||
|
||||
static propTypes = {
|
||||
specSelectors: PropTypes.object.isRequired,
|
||||
layoutSelectors: PropTypes.object.isRequired,
|
||||
layoutActions: PropTypes.object.isRequired,
|
||||
getComponent: PropTypes.func.isRequired,
|
||||
}
|
||||
|
||||
onFilterChange = (e) => {
|
||||
const {target: {value}} = e
|
||||
this.props.layoutActions.updateFilter(value)
|
||||
}
|
||||
|
||||
render () {
|
||||
const {specSelectors, layoutSelectors, getComponent} = this.props
|
||||
const Col = getComponent("Col")
|
||||
|
||||
const isLoading = specSelectors.loadingStatus() === "loading"
|
||||
const isFailed = specSelectors.loadingStatus() === "failed"
|
||||
const filter = layoutSelectors.currentFilter()
|
||||
|
||||
const inputStyle = {}
|
||||
if (isFailed) inputStyle.color = "red"
|
||||
if (isLoading) inputStyle.color = "#aaa"
|
||||
|
||||
return (
|
||||
<div>
|
||||
{filter === null || filter === false ? null :
|
||||
<div className="filter-container">
|
||||
<Col className="filter wrapper" mobile={12}>
|
||||
<input className="operation-filter-input" placeholder="Filter by tag" type="text"
|
||||
onChange={this.onFilterChange} value={filter === true || filter === "true" ? "" : filter}
|
||||
disabled={isLoading} style={inputStyle}/>
|
||||
</Col>
|
||||
</div>
|
||||
}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
|
||||
export default class InfoContainer extends React.Component {
|
||||
|
||||
static propTypes = {
|
||||
specActions: PropTypes.object.isRequired,
|
||||
specSelectors: PropTypes.object.isRequired,
|
||||
getComponent: PropTypes.func.isRequired,
|
||||
}
|
||||
|
||||
render () {
|
||||
const {specSelectors, getComponent} = this.props
|
||||
|
||||
const info = specSelectors.info()
|
||||
const url = specSelectors.url()
|
||||
const basePath = specSelectors.basePath()
|
||||
const host = specSelectors.host()
|
||||
const externalDocs = specSelectors.externalDocs()
|
||||
|
||||
const Info = getComponent("info")
|
||||
|
||||
return (
|
||||
<div>
|
||||
{info && info.count() ? (
|
||||
<Info info={info} url={url} host={host} basePath={basePath} externalDocs={externalDocs}
|
||||
getComponent={getComponent}/>
|
||||
) : null}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
|
||||
export default class SchemesContainer extends React.Component {
|
||||
|
||||
static propTypes = {
|
||||
specActions: PropTypes.object.isRequired,
|
||||
specSelectors: PropTypes.object.isRequired,
|
||||
getComponent: PropTypes.func.isRequired,
|
||||
}
|
||||
|
||||
render () {
|
||||
const {specActions, specSelectors, getComponent} = this.props
|
||||
const currentScheme = specSelectors.operationScheme()
|
||||
const schemes = specSelectors.schemes()
|
||||
const securityDefinitions = specSelectors.securityDefinitions()
|
||||
|
||||
const Col = getComponent("Col")
|
||||
const AuthorizeBtn = getComponent("authorizeBtn", true)
|
||||
const Schemes = getComponent("schemes")
|
||||
|
||||
return (
|
||||
<div>
|
||||
{schemes && schemes.size || securityDefinitions ? (
|
||||
<div className="scheme-container">
|
||||
<Col className="schemes wrapper" mobile={12}>
|
||||
{schemes && schemes.size ? (
|
||||
<Schemes
|
||||
currentScheme={currentScheme}
|
||||
schemes={schemes}
|
||||
specActions={specActions}
|
||||
/>
|
||||
) : null}
|
||||
{securityDefinitions ? (
|
||||
<AuthorizeBtn/>
|
||||
) : null}
|
||||
</Col>
|
||||
</div>
|
||||
) : null}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
+6
-7
@@ -27,7 +27,7 @@ module.exports = function SwaggerUI(opts) {
|
||||
|
||||
const defaults = {
|
||||
// Some general settings, that we floated to the top
|
||||
dom_id: null,
|
||||
dom_id: null, // eslint-disable-line camelcase
|
||||
domNode: null,
|
||||
spec: {},
|
||||
url: "",
|
||||
@@ -131,10 +131,6 @@ module.exports = function SwaggerUI(opts) {
|
||||
var system = store.getSystem()
|
||||
|
||||
const downloadSpec = (fetchedConfig) => {
|
||||
if(typeof constructorConfig !== "object") {
|
||||
return system
|
||||
}
|
||||
|
||||
let localConfig = system.specSelectors.getLocalConfig ? system.specSelectors.getLocalConfig() : {}
|
||||
let mergedConfig = deepExtend({}, localConfig, constructorConfig, fetchedConfig || {}, queryConfig)
|
||||
|
||||
@@ -144,6 +140,7 @@ module.exports = function SwaggerUI(opts) {
|
||||
}
|
||||
|
||||
store.setConfigs(mergedConfig)
|
||||
system.configsActions.loaded()
|
||||
|
||||
if (fetchedConfig !== null) {
|
||||
if (!queryConfig.url && typeof mergedConfig.spec === "object" && Object.keys(mergedConfig.spec).length) {
|
||||
@@ -171,15 +168,17 @@ module.exports = function SwaggerUI(opts) {
|
||||
return system
|
||||
}
|
||||
|
||||
let configUrl = queryConfig.config || constructorConfig.configUrl
|
||||
const configUrl = queryConfig.config || constructorConfig.configUrl
|
||||
|
||||
if (!configUrl || !system.specActions.getConfigByUrl || system.specActions.getConfigByUrl && !system.specActions.getConfigByUrl({
|
||||
if (!configUrl || !system.specActions || !system.specActions.getConfigByUrl || system.specActions.getConfigByUrl && !system.specActions.getConfigByUrl({
|
||||
url: configUrl,
|
||||
loadRemoteConfig: true,
|
||||
requestInterceptor: constructorConfig.requestInterceptor,
|
||||
responseInterceptor: constructorConfig.responseInterceptor,
|
||||
}, downloadSpec)) {
|
||||
return downloadSpec()
|
||||
} else {
|
||||
system.specActions.getConfigByUrl(configUrl, downloadSpec)
|
||||
}
|
||||
|
||||
return system
|
||||
|
||||
@@ -201,7 +201,7 @@ export class JsonSchema_boolean extends Component {
|
||||
|
||||
onEnumChange = (val) => this.props.onChange(val)
|
||||
render() {
|
||||
let { getComponent, value, errors, schema } = this.props
|
||||
let { getComponent, value, errors, schema, required } = this.props
|
||||
errors = errors.toJS ? errors.toJS() : []
|
||||
|
||||
const Select = getComponent("Select")
|
||||
@@ -210,7 +210,7 @@ export class JsonSchema_boolean extends Component {
|
||||
title={ errors.length ? errors : ""}
|
||||
value={ String(value) }
|
||||
allowedValues={ fromJS(schema.enum || ["true", "false"]) }
|
||||
allowEmptyValue={ !this.props.required }
|
||||
allowEmptyValue={ !schema.enum || !required }
|
||||
onChange={ this.onEnumChange }/>)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,3 +18,7 @@ export function toggle(configName) {
|
||||
payload: configName,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Hook
|
||||
export const loaded = () => () => {}
|
||||
|
||||
@@ -1,18 +1,23 @@
|
||||
// import reducers from "./reducers"
|
||||
// import * as actions from "./actions"
|
||||
// import * as selectors from "./selectors"
|
||||
import * as specWrapActions from "./spec-wrap-actions"
|
||||
import * as layoutWrapActions from "./layout-wrap-actions"
|
||||
import layout from "./layout"
|
||||
import OperationWrapper from "./operation-wrapper"
|
||||
import OperationTagWrapper from "./operation-tag-wrapper"
|
||||
|
||||
export default function() {
|
||||
return {
|
||||
return [layout, {
|
||||
statePlugins: {
|
||||
spec: {
|
||||
wrapActions: specWrapActions
|
||||
},
|
||||
layout: {
|
||||
wrapActions: layoutWrapActions
|
||||
configs: {
|
||||
wrapActions: {
|
||||
loaded: (ori, system) => (...args) => {
|
||||
ori(...args)
|
||||
const hash = window.location.hash
|
||||
system.layoutActions.parseDeepLinkHash(hash)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
wrapComponents: {
|
||||
operation: OperationWrapper,
|
||||
OperationTag: OperationTagWrapper,
|
||||
},
|
||||
}]
|
||||
}
|
||||
|
||||
@@ -1,37 +0,0 @@
|
||||
import { setHash } from "./helpers"
|
||||
import { createDeepLinkPath } from "core/utils"
|
||||
|
||||
export const show = (ori, { getConfigs }) => (...args) => {
|
||||
ori(...args)
|
||||
|
||||
const isDeepLinkingEnabled = getConfigs().deepLinking
|
||||
if(!isDeepLinkingEnabled || isDeepLinkingEnabled === "false") {
|
||||
return
|
||||
}
|
||||
|
||||
try {
|
||||
let [thing, shown] = args
|
||||
let [type] = thing
|
||||
|
||||
if(type === "operations-tag" || type === "operations") {
|
||||
if(!shown) {
|
||||
return setHash("/")
|
||||
}
|
||||
|
||||
if(type === "operations") {
|
||||
let [, tag, operationId] = thing
|
||||
setHash(`/${createDeepLinkPath(tag)}/${createDeepLinkPath(operationId)}`)
|
||||
}
|
||||
|
||||
if(type === "operations-tag") {
|
||||
let [, tag] = thing
|
||||
setHash(`/${createDeepLinkPath(tag)}`)
|
||||
}
|
||||
}
|
||||
|
||||
} catch(e) {
|
||||
// This functionality is not mission critical, so if something goes wrong
|
||||
// we'll just move on
|
||||
console.error(e)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,181 @@
|
||||
import { setHash } from "./helpers"
|
||||
import zenscroll from "zenscroll"
|
||||
import Im, { fromJS } from "immutable"
|
||||
|
||||
const SCROLL_TO = "layout_scroll_to"
|
||||
const CLEAR_SCROLL_TO = "layout_clear_scroll"
|
||||
|
||||
export const show = (ori, { getConfigs, layoutSelectors }) => (...args) => {
|
||||
ori(...args)
|
||||
|
||||
if(!getConfigs().deepLinking) {
|
||||
return
|
||||
}
|
||||
|
||||
try {
|
||||
let [tokenArray, shown] = args
|
||||
//Coerce in to array
|
||||
tokenArray = Array.isArray(tokenArray) ? tokenArray : [tokenArray]
|
||||
// Convert into something we can put in the URL hash
|
||||
// Or return empty, if we cannot
|
||||
const urlHashArray = layoutSelectors.urlHashArrayFromIsShownKey(tokenArray) // Will convert
|
||||
|
||||
// No hash friendly list?
|
||||
if(!urlHashArray.length)
|
||||
return
|
||||
|
||||
const [type, assetName] = urlHashArray
|
||||
|
||||
if (!shown) {
|
||||
return setHash("/")
|
||||
}
|
||||
|
||||
if (urlHashArray.length === 2) {
|
||||
setHash(`/${type}/${assetName}`)
|
||||
} else if (urlHashArray.length === 1) {
|
||||
setHash(`/${type}`)
|
||||
}
|
||||
|
||||
} catch (e) {
|
||||
// This functionality is not mission critical, so if something goes wrong
|
||||
// we'll just move on
|
||||
console.error(e) // eslint-disable-line no-console
|
||||
}
|
||||
}
|
||||
|
||||
export const scrollTo = (path) => {
|
||||
return {
|
||||
type: SCROLL_TO,
|
||||
payload: Array.isArray(path) ? path : [path]
|
||||
}
|
||||
}
|
||||
|
||||
export const parseDeepLinkHash = (rawHash) => ({ layoutActions, layoutSelectors, getConfigs }) => {
|
||||
|
||||
if(!getConfigs().deepLinking) {
|
||||
return
|
||||
}
|
||||
|
||||
if(rawHash) {
|
||||
let hash = rawHash.slice(1) // # is first character
|
||||
|
||||
|
||||
if(hash[0] === "!") {
|
||||
// Parse UI 2.x shebangs
|
||||
hash = hash.slice(1)
|
||||
}
|
||||
|
||||
if(hash[0] === "/") {
|
||||
// "/pet/addPet" => "pet/addPet"
|
||||
// makes the split result cleaner
|
||||
// also handles forgotten leading slash
|
||||
hash = hash.slice(1)
|
||||
}
|
||||
|
||||
const isShownKey = layoutSelectors.isShownKeyFromUrlHashArray(hash.split("/"))
|
||||
|
||||
layoutActions.show(isShownKey, true) // TODO: 'show' operation tag
|
||||
layoutActions.scrollTo(isShownKey)
|
||||
}
|
||||
}
|
||||
|
||||
export const readyToScroll = (isShownKey, ref) => (system) => {
|
||||
const scrollToKey = system.layoutSelectors.getScrollToKey()
|
||||
|
||||
if(Im.is(scrollToKey, fromJS(isShownKey))) {
|
||||
system.layoutActions.scrollToElement(ref)
|
||||
system.layoutActions.clearScrollTo()
|
||||
}
|
||||
}
|
||||
|
||||
// Scroll to "ref" (dom node) with the scrollbar on "container" or the nearest parent
|
||||
export const scrollToElement = (ref, container) => (system) => {
|
||||
try {
|
||||
container = container || system.fn.getScrollParent(ref)
|
||||
let myScroller = zenscroll.createScroller(container)
|
||||
myScroller.to(ref)
|
||||
} catch(e) {
|
||||
console.error(e) // eslint-disable-line no-console
|
||||
}
|
||||
}
|
||||
|
||||
export const clearScrollTo = () => {
|
||||
return {
|
||||
type: CLEAR_SCROLL_TO,
|
||||
}
|
||||
}
|
||||
|
||||
// From: https://stackoverflow.com/a/42543908/3933724
|
||||
// Modified to return html instead of body element as last resort
|
||||
function getScrollParent(element, includeHidden) {
|
||||
const LAST_RESORT = document.documentElement
|
||||
let style = getComputedStyle(element)
|
||||
const excludeStaticParent = style.position === "absolute"
|
||||
const overflowRegex = includeHidden ? /(auto|scroll|hidden)/ : /(auto|scroll)/
|
||||
|
||||
if (style.position === "fixed")
|
||||
return LAST_RESORT
|
||||
for (let parent = element; (parent = parent.parentElement);) {
|
||||
style = getComputedStyle(parent)
|
||||
if (excludeStaticParent && style.position === "static") {
|
||||
continue
|
||||
}
|
||||
if (overflowRegex.test(style.overflow + style.overflowY + style.overflowX))
|
||||
return parent
|
||||
}
|
||||
|
||||
return LAST_RESORT
|
||||
}
|
||||
|
||||
export default {
|
||||
fn: {
|
||||
getScrollParent,
|
||||
},
|
||||
statePlugins: {
|
||||
layout: {
|
||||
actions: {
|
||||
scrollToElement,
|
||||
scrollTo,
|
||||
clearScrollTo,
|
||||
readyToScroll,
|
||||
parseDeepLinkHash
|
||||
},
|
||||
selectors: {
|
||||
getScrollToKey(state) {
|
||||
return state.get("scrollToKey")
|
||||
},
|
||||
isShownKeyFromUrlHashArray(state, urlHashArray) {
|
||||
const [tag, operationId] = urlHashArray
|
||||
// We only put operations in the URL
|
||||
if(operationId) {
|
||||
return ["operations", tag, operationId]
|
||||
} else if (tag) {
|
||||
return ["operations-tag", tag]
|
||||
}
|
||||
return []
|
||||
},
|
||||
urlHashArrayFromIsShownKey(state, isShownKey) {
|
||||
let [type, tag, operationId] = isShownKey
|
||||
// We only put operations in the URL
|
||||
if(type == "operations") {
|
||||
return [tag, operationId]
|
||||
} else if (type == "operations-tag") {
|
||||
return [tag]
|
||||
}
|
||||
return []
|
||||
},
|
||||
},
|
||||
reducers: {
|
||||
[SCROLL_TO](state, action) {
|
||||
return state.set("scrollToKey", Im.fromJS(action.payload))
|
||||
},
|
||||
[CLEAR_SCROLL_TO](state) {
|
||||
return state.delete("scrollToKey")
|
||||
}
|
||||
},
|
||||
wrapActions: {
|
||||
show
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
import React from "react"
|
||||
import { PropTypes } from "prop-types"
|
||||
|
||||
const Wrapper = (Ori, system) => class OperationTagWrapper extends React.Component {
|
||||
|
||||
static propTypes = {
|
||||
tag: PropTypes.object.isRequired,
|
||||
}
|
||||
|
||||
onLoad = (ref) => {
|
||||
const { tag } = this.props
|
||||
const isShownKey = ["operations-tag", tag]
|
||||
system.layoutActions.readyToScroll(isShownKey, ref)
|
||||
}
|
||||
|
||||
render() {
|
||||
return (
|
||||
<span ref={this.onLoad}>
|
||||
<Ori {...this.props} />
|
||||
</span>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
export default Wrapper
|
||||
@@ -0,0 +1,26 @@
|
||||
import React from "react"
|
||||
import ImPropTypes from "react-immutable-proptypes"
|
||||
|
||||
const Wrapper = (Ori, system) => class OperationWrapper extends React.Component {
|
||||
|
||||
static propTypes = {
|
||||
operation: ImPropTypes.map.isRequired,
|
||||
}
|
||||
|
||||
onLoad = (ref) => {
|
||||
const { operation } = this.props
|
||||
const { tag, operationId } = operation.toObject()
|
||||
const isShownKey = ["operations", tag, operationId]
|
||||
system.layoutActions.readyToScroll(isShownKey, ref)
|
||||
}
|
||||
|
||||
render() {
|
||||
return (
|
||||
<span ref={this.onLoad}>
|
||||
<Ori {...this.props} />
|
||||
</span>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
export default Wrapper
|
||||
@@ -1,64 +0,0 @@
|
||||
import zenscroll from "zenscroll"
|
||||
import { escapeDeepLinkPath } from "core/utils"
|
||||
|
||||
let hasHashBeenParsed = false //TODO this forces code to only run once which may prevent scrolling if page not refreshed
|
||||
|
||||
|
||||
export const updateJsonSpec = (ori, { layoutActions, getConfigs }) => (...args) => {
|
||||
ori(...args)
|
||||
|
||||
const isDeepLinkingEnabled = getConfigs().deepLinking
|
||||
if(!isDeepLinkingEnabled || isDeepLinkingEnabled === "false") {
|
||||
return
|
||||
}
|
||||
if(window.location.hash && !hasHashBeenParsed ) {
|
||||
let hash = window.location.hash.slice(1) // # is first character
|
||||
|
||||
if(hash[0] === "!") {
|
||||
// Parse UI 2.x shebangs
|
||||
hash = hash.slice(1)
|
||||
}
|
||||
|
||||
if(hash[0] === "/") {
|
||||
// "/pet/addPet" => "pet/addPet"
|
||||
// makes the split result cleaner
|
||||
// also handles forgotten leading slash
|
||||
hash = hash.slice(1)
|
||||
}
|
||||
|
||||
let [tag, operationId] = hash.split("/")
|
||||
|
||||
let swaggerUI = document.querySelector(".swagger-ui")
|
||||
let myScroller = zenscroll.createScroller(swaggerUI)
|
||||
|
||||
let target
|
||||
|
||||
if(tag && operationId) {
|
||||
// Pre-expand and scroll to the operation
|
||||
layoutActions.show(["operations-tag", tag], true)
|
||||
layoutActions.show(["operations", tag, operationId], true)
|
||||
|
||||
target = document
|
||||
.getElementById(`operations-${escapeDeepLinkPath(tag)}-${escapeDeepLinkPath(operationId)}`)
|
||||
} else if(tag) {
|
||||
// Pre-expand and scroll to the tag
|
||||
layoutActions.show(["operations-tag", tag], true)
|
||||
|
||||
target = document.getElementById(`operations-tag-${escapeDeepLinkPath(tag)}`)
|
||||
}
|
||||
|
||||
|
||||
if(target) {
|
||||
myScroller.to(target)
|
||||
setTimeout(() => {
|
||||
// Backup functionality: if we're still at the top of the document,
|
||||
// scroll on the entire page (not within the Swagger-UI container)
|
||||
if(zenscroll.getY() === 0) {
|
||||
zenscroll.to(target)
|
||||
}
|
||||
}, 50)
|
||||
}
|
||||
}
|
||||
|
||||
hasHashBeenParsed = true
|
||||
}
|
||||
@@ -2,6 +2,7 @@ import Callbacks from "./callbacks"
|
||||
import RequestBody from "./request-body"
|
||||
import OperationLink from "./operation-link.jsx"
|
||||
import Servers from "./servers"
|
||||
import ServersContainer from "./servers-container"
|
||||
import RequestBodyEditor from "./request-body-editor"
|
||||
import HttpAuth from "./http-auth"
|
||||
import OperationServers from "./operation-servers"
|
||||
@@ -11,6 +12,7 @@ export default {
|
||||
HttpAuth,
|
||||
RequestBody,
|
||||
Servers,
|
||||
ServersContainer,
|
||||
RequestBodyEditor,
|
||||
OperationServers,
|
||||
operationLink: OperationLink
|
||||
|
||||
@@ -0,0 +1,42 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
|
||||
export default class ServersContainer extends React.Component {
|
||||
|
||||
static propTypes = {
|
||||
specSelectors: PropTypes.object.isRequired,
|
||||
oas3Selectors: PropTypes.object.isRequired,
|
||||
oas3Actions: PropTypes.object.isRequired,
|
||||
getComponent: PropTypes.func.isRequired,
|
||||
}
|
||||
|
||||
render () {
|
||||
const {specSelectors, oas3Selectors, oas3Actions, getComponent} = this.props
|
||||
|
||||
const servers = specSelectors.servers()
|
||||
|
||||
const Col = getComponent("Col")
|
||||
const Servers = getComponent("Servers")
|
||||
|
||||
return (
|
||||
<div>
|
||||
{servers && servers.size ? (
|
||||
<div className="global-server-container">
|
||||
<Col className="servers wrapper" mobile={12}>
|
||||
<span className="servers-title">Server</span>
|
||||
<Servers
|
||||
servers={servers}
|
||||
currentServer={oas3Selectors.selectedServer()}
|
||||
setSelectedServer={oas3Actions.setSelectedServer}
|
||||
setServerVariableValue={oas3Actions.setServerVariableValue}
|
||||
getServerVariable={oas3Selectors.serverVariableValue}
|
||||
getEffectiveServerValue={oas3Selectors.serverEffectiveValue}
|
||||
/>
|
||||
</Col>
|
||||
</div>
|
||||
|
||||
) : null}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -6,7 +6,7 @@ export function isOAS3(jsSpec) {
|
||||
return false
|
||||
}
|
||||
|
||||
return oasVersion.startsWith("3")
|
||||
return oasVersion.startsWith("3.0.")
|
||||
}
|
||||
|
||||
export function isSwagger2(jsSpec) {
|
||||
@@ -15,7 +15,7 @@ export function isSwagger2(jsSpec) {
|
||||
return false
|
||||
}
|
||||
|
||||
return swaggerVersion.startsWith("2")
|
||||
return swaggerVersion.startsWith("2.0")
|
||||
}
|
||||
|
||||
export function OAS3ComponentWrapFactory(Component) {
|
||||
|
||||
@@ -31,6 +31,7 @@ import Clear from "core/components/clear"
|
||||
import LiveResponse from "core/components/live-response"
|
||||
import OnlineValidatorBadge from "core/components/online-validator-badge"
|
||||
import Operations from "core/components/operations"
|
||||
import OperationTag from "core/components/operation-tag"
|
||||
import Operation from "core/components/operation"
|
||||
import OperationExt from "core/components/operation-extensions"
|
||||
import OperationExtRow from "core/components/operation-extension-row"
|
||||
@@ -50,10 +51,13 @@ import Info, {
|
||||
InfoUrl,
|
||||
InfoBasePath
|
||||
} from "core/components/info"
|
||||
import InfoContainer from "core/containers/info"
|
||||
import Footer from "core/components/footer"
|
||||
import FilterContainer from "core/containers/filter"
|
||||
import ParamBody from "core/components/param-body"
|
||||
import Curl from "core/components/curl"
|
||||
import Schemes from "core/components/schemes"
|
||||
import SchemesContainer from "core/containers/schemes"
|
||||
import ModelCollapse from "core/components/model-collapse"
|
||||
import ModelExample from "core/components/model-example"
|
||||
import ModelWrapper from "core/components/model-wrapper"
|
||||
@@ -65,6 +69,7 @@ import ArrayModel from "core/components/array-model"
|
||||
import PrimitiveModel from "core/components/primitive-model"
|
||||
import Property from "core/components/property"
|
||||
import TryItOutButton from "core/components/try-it-out-button"
|
||||
import VersionPragmaFilter from "core/components/version-pragma-filter"
|
||||
import VersionStamp from "core/components/version-stamp"
|
||||
import DeepLink from "core/components/deep-link"
|
||||
import SvgAssets from "core/components/svg-assets"
|
||||
@@ -93,6 +98,7 @@ export default function() {
|
||||
clear: Clear,
|
||||
liveResponse: LiveResponse,
|
||||
info: Info,
|
||||
InfoContainer,
|
||||
onlineValidatorBadge: OnlineValidatorBadge,
|
||||
operations: Operations,
|
||||
operation: Operation,
|
||||
@@ -108,9 +114,11 @@ export default function() {
|
||||
contentType: ContentType,
|
||||
overview: Overview,
|
||||
footer: Footer,
|
||||
FilterContainer,
|
||||
ParamBody: ParamBody,
|
||||
curl: Curl,
|
||||
schemes: Schemes,
|
||||
SchemesContainer,
|
||||
modelExample: ModelExample,
|
||||
ModelWrapper,
|
||||
ModelCollapse,
|
||||
@@ -124,10 +132,12 @@ export default function() {
|
||||
TryItOutButton,
|
||||
Markdown,
|
||||
BaseLayout,
|
||||
VersionPragmaFilter,
|
||||
VersionStamp,
|
||||
OperationExt,
|
||||
OperationExtRow,
|
||||
ParameterExt,
|
||||
OperationTag,
|
||||
OperationContainer,
|
||||
DeepLink,
|
||||
InfoUrl,
|
||||
|
||||
+1
-1
@@ -37,7 +37,7 @@ export function objectify (thing) {
|
||||
if(!isObject(thing))
|
||||
return {}
|
||||
if(isImmutable(thing))
|
||||
return thing.toObject()
|
||||
return thing.toJS()
|
||||
return thing
|
||||
}
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ Here is an example of each `type`
|
||||
```js
|
||||
// A contrived, but quite full example....
|
||||
|
||||
export function SomePlugin( toolbox ) {
|
||||
export function SomePlugin(toolbox) {
|
||||
|
||||
const UPDATE_SOMETHING = "some_namespace_update_something" // strings just need to be uniuqe... see below
|
||||
|
||||
|
||||
@@ -796,3 +796,30 @@ a.nostyle {
|
||||
cursor: pointer;
|
||||
}
|
||||
}
|
||||
|
||||
.version-pragma {
|
||||
height: 100%;
|
||||
padding: 5em 0px;
|
||||
|
||||
&__message {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
height: 100%;
|
||||
font-size: 1.2em;
|
||||
text-align: center;
|
||||
line-height: 1.5em;
|
||||
|
||||
padding: 0px .6em;
|
||||
|
||||
> div {
|
||||
max-width: 55ch;
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
code {
|
||||
background-color: #dedede;
|
||||
padding: 4px 4px 2px;
|
||||
white-space: pre;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
---
|
||||
url: "http://petstore.swagger.io/v2/swagger.json"
|
||||
url: "https://petstore.swagger.io/v2/swagger.json"
|
||||
dom_id: "#swagger-ui"
|
||||
validatorUrl: "https://online.swagger.io/validator"
|
||||
oauth2RedirectUrl: "http://localhost:3200/oauth2-redirect.html"
|
||||
|
||||
@@ -0,0 +1,65 @@
|
||||
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect from "expect"
|
||||
import { mount } from "enzyme"
|
||||
import FilterContainer from "containers/filter"
|
||||
import { Col } from "components/layout-utils"
|
||||
|
||||
describe("<FilterContainer/>", function(){
|
||||
|
||||
const mockedProps = {
|
||||
specSelectors: {
|
||||
loadingStatus() {}
|
||||
},
|
||||
layoutSelectors: {
|
||||
currentFilter() {}
|
||||
},
|
||||
getComponent: () => {return Col}
|
||||
}
|
||||
|
||||
it("renders FilterContainer if filter is provided", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.layoutSelectors = {...mockedProps.specSelectors}
|
||||
props.layoutSelectors.currentFilter = function() {return true}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<FilterContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedColInsideFilter = wrapper.find(Col)
|
||||
expect(renderedColInsideFilter.length).toEqual(1)
|
||||
})
|
||||
|
||||
it("does not render FilterContainer if filter is null", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.layoutSelectors = {...mockedProps.specSelectors}
|
||||
props.layoutSelectors.currentFilter = function() {return null}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<FilterContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedColInsideFilter = wrapper.find(Col)
|
||||
expect(renderedColInsideFilter.length).toEqual(0)
|
||||
})
|
||||
|
||||
it("does not render FilterContainer if filter is false", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.layoutSelectors = {...mockedProps.specSelectors}
|
||||
props.layoutSelectors.currentFilter = function() {return false}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<FilterContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedColInsideFilter = wrapper.find(Col)
|
||||
expect(renderedColInsideFilter.length).toEqual(0)
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,67 @@
|
||||
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect from "expect"
|
||||
import { mount } from "enzyme"
|
||||
import { fromJS } from "immutable"
|
||||
import InfoContainer from "containers/info"
|
||||
|
||||
describe("<InfoContainer/>", function () {
|
||||
|
||||
const components = {
|
||||
info: () => <span className="mocked-info"/>
|
||||
}
|
||||
const mockedProps = {
|
||||
specSelectors: {
|
||||
info () {},
|
||||
url () {},
|
||||
basePath () {},
|
||||
host () {},
|
||||
externalDocs () {}
|
||||
},
|
||||
getComponent: c => components[c]
|
||||
}
|
||||
|
||||
it("renders Info inside InfoContainer if info is provided", function () {
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.info = function () {return fromJS(["info1", "info2"])}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<InfoContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedInfo = wrapper.find("span.mocked-info")
|
||||
expect(renderedInfo.length).toEqual(1)
|
||||
})
|
||||
|
||||
it("does not render Info inside InfoContainer if no info is provided", function () {
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.info = function () {return fromJS([])}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<InfoContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedInfo = wrapper.find("span.mocked-info")
|
||||
expect(renderedInfo.length).toEqual(0)
|
||||
})
|
||||
|
||||
it("does not render Info inside InfoContainer if info is undefined", function () {
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<InfoContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedInfo = wrapper.find("span.mocked-info")
|
||||
expect(renderedInfo.length).toEqual(0)
|
||||
})
|
||||
})
|
||||
@@ -86,6 +86,54 @@ describe("<JsonSchemaForm/>", function(){
|
||||
expect(wrapper.find("select option").eq(2).text()).toEqual("false")
|
||||
})
|
||||
|
||||
|
||||
it("should render the correct options for an enum boolean parameter", function(){
|
||||
|
||||
let props = {
|
||||
getComponent: getComponentStub,
|
||||
value: "",
|
||||
onChange: () => {},
|
||||
keyName: "",
|
||||
fn: {},
|
||||
schema: {
|
||||
type: "boolean",
|
||||
enum: ["true"]
|
||||
}
|
||||
}
|
||||
|
||||
let wrapper = render(<JsonSchemaForm {...props}/>)
|
||||
|
||||
expect(wrapper.find("select").length).toEqual(1)
|
||||
expect(wrapper.find("select option").length).toEqual(2)
|
||||
expect(wrapper.find("select option").eq(0).text()).toEqual("--")
|
||||
expect(wrapper.find("select option").eq(1).text()).toEqual("true")
|
||||
expect(wrapper.find("select option:checked").first().text()).toEqual("--")
|
||||
})
|
||||
|
||||
it("should render the correct options for a required boolean parameter", function(){
|
||||
|
||||
let props = {
|
||||
getComponent: getComponentStub,
|
||||
value: "",
|
||||
onChange: () => {},
|
||||
keyName: "",
|
||||
fn: {},
|
||||
schema: {
|
||||
type: "boolean",
|
||||
required: true
|
||||
}
|
||||
}
|
||||
|
||||
let wrapper = render(<JsonSchemaForm {...props}/>)
|
||||
|
||||
expect(wrapper.find("select").length).toEqual(1)
|
||||
expect(wrapper.find("select option").length).toEqual(3)
|
||||
expect(wrapper.find("select option").eq(0).text()).toEqual("--")
|
||||
expect(wrapper.find("select option").eq(1).text()).toEqual("true")
|
||||
expect(wrapper.find("select option").eq(2).text()).toEqual("false")
|
||||
expect(wrapper.find("select option:checked").first().text()).toEqual("--")
|
||||
})
|
||||
|
||||
it("should render the correct options for a required enum boolean parameter", function(){
|
||||
|
||||
let props = {
|
||||
@@ -105,7 +153,8 @@ describe("<JsonSchemaForm/>", function(){
|
||||
|
||||
expect(wrapper.find("select").length).toEqual(1)
|
||||
expect(wrapper.find("select option").length).toEqual(1)
|
||||
expect(wrapper.find("select option").first().text()).toEqual("true")
|
||||
expect(wrapper.find("select option").eq(0).text()).toEqual("true")
|
||||
expect(wrapper.find("select option:checked").first().text()).toEqual("true")
|
||||
})
|
||||
})
|
||||
describe("objects", function() {
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect, { createSpy } from "expect"
|
||||
import expect from "expect"
|
||||
import { render } from "enzyme"
|
||||
import { fromJS } from "immutable"
|
||||
import DeepLink from "components/deep-link"
|
||||
@@ -10,7 +10,8 @@ import {Collapse} from "components/layout-utils"
|
||||
const components = {
|
||||
Collapse,
|
||||
DeepLink,
|
||||
OperationContainer: ({ path, method }) => <span className="mocked-op" id={`${path}-${method}`} />
|
||||
OperationContainer: ({ path, method }) => <span className="mocked-op" id={`${path}-${method}`} />,
|
||||
OperationTag: "div",
|
||||
}
|
||||
|
||||
describe("<Operations/>", function(){
|
||||
|
||||
@@ -0,0 +1,119 @@
|
||||
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect from "expect"
|
||||
import { mount, render } from "enzyme"
|
||||
import { fromJS } from "immutable"
|
||||
import SchemesContainer from "containers/schemes"
|
||||
import Schemes from "components/schemes"
|
||||
import { Col } from "components/layout-utils"
|
||||
|
||||
describe("<SchemesContainer/>", function(){
|
||||
|
||||
const components = {
|
||||
schemes: Schemes,
|
||||
Col,
|
||||
authorizeBtn: () => <span className="mocked-button" id="mocked-button" />
|
||||
}
|
||||
const mockedProps = {
|
||||
specSelectors: {
|
||||
securityDefinitions() {},
|
||||
operationScheme() {},
|
||||
schemes() {}
|
||||
},
|
||||
specActions: {
|
||||
setScheme() {}
|
||||
},
|
||||
getComponent: c => components[c]
|
||||
}
|
||||
const twoSecurityDefinitions = {
|
||||
"petstore_auth": {
|
||||
"type": "oauth2",
|
||||
"authorizationUrl": "http://petstore.swagger.io/oauth/dialog",
|
||||
"flow": "implicit",
|
||||
"scopes": {
|
||||
"write:pets": "modify pets in your account",
|
||||
"read:pets": "read your pets"
|
||||
}
|
||||
},
|
||||
"api_key": {
|
||||
"type": "apiKey",
|
||||
"name": "api_key",
|
||||
"in": "header"
|
||||
}
|
||||
}
|
||||
|
||||
it("renders Schemes inside SchemesContainer if schemes are provided", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.operationScheme = function() {return "http"}
|
||||
props.specSelectors.schemes = function() {return fromJS(["http", "https"])}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<SchemesContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedSchemes = wrapper.find(Schemes)
|
||||
expect(renderedSchemes.length).toEqual(1)
|
||||
})
|
||||
|
||||
it("does not render Schemes inside SchemeWrapper if empty array of schemes is provided", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.schemes = function() {return fromJS([])}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<SchemesContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedSchemes = wrapper.find(Schemes)
|
||||
expect(renderedSchemes.length).toEqual(0)
|
||||
})
|
||||
|
||||
it("does not render Schemes inside SchemeWrapper if provided schemes are undefined", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.schemes = function() {return undefined}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<SchemesContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedSchemes = wrapper.find(Schemes)
|
||||
expect(renderedSchemes.length).toEqual(0)
|
||||
})
|
||||
|
||||
it("renders AuthorizeBtn inside SchemesContainer if security definition is provided", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.securityDefinitions = function () {return fromJS(twoSecurityDefinitions)}
|
||||
|
||||
// When
|
||||
let wrapper = render(<SchemesContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedAuthorizeBtn = wrapper.find("span.mocked-button")
|
||||
expect(renderedAuthorizeBtn.length).toEqual(1)
|
||||
})
|
||||
|
||||
it("does not render AuthorizeBtn if security definition is not provided", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
|
||||
// When
|
||||
let wrapper = render(<SchemesContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedAuthorizeBtn = wrapper.find("span.mocked-button")
|
||||
expect(renderedAuthorizeBtn.length).toEqual(0)
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,70 @@
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect, { createSpy } from "expect"
|
||||
import { shallow } from "enzyme"
|
||||
import { fromJS, Map } from "immutable"
|
||||
import VersionPragmaFilter from "components/version-pragma-filter"
|
||||
|
||||
describe("<VersionPragmaFilter/>", function(){
|
||||
it("renders children for a Swagger 2 definition", function(){
|
||||
// When
|
||||
let wrapper = shallow(
|
||||
<VersionPragmaFilter isSwagger2={true} isOAS3={false}>
|
||||
hello!
|
||||
</VersionPragmaFilter>
|
||||
)
|
||||
|
||||
// Then
|
||||
expect(wrapper.find("div").length).toEqual(1)
|
||||
expect(wrapper.find("div").text()).toEqual("hello!")
|
||||
})
|
||||
it("renders children for an OpenAPI 3 definition", function(){
|
||||
// When
|
||||
let wrapper = shallow(
|
||||
<VersionPragmaFilter isSwagger2={false} isOAS3={true}>
|
||||
hello!
|
||||
</VersionPragmaFilter>
|
||||
)
|
||||
|
||||
// Then
|
||||
expect(wrapper.find("div").length).toEqual(1)
|
||||
expect(wrapper.find("div").text()).toEqual("hello!")
|
||||
})
|
||||
it("renders children when a bypass prop is set", function(){
|
||||
// When
|
||||
let wrapper = shallow(
|
||||
<VersionPragmaFilter bypass>
|
||||
hello!
|
||||
</VersionPragmaFilter>
|
||||
)
|
||||
|
||||
// Then
|
||||
expect(wrapper.find("div").length).toEqual(1)
|
||||
expect(wrapper.find("div").text()).toEqual("hello!")
|
||||
})
|
||||
it("renders the correct message for an ambiguous-version definition", function(){
|
||||
// When
|
||||
let wrapper = shallow(
|
||||
<VersionPragmaFilter isSwagger2={true} isOAS3={true}>
|
||||
hello!
|
||||
</VersionPragmaFilter>
|
||||
)
|
||||
|
||||
// Then
|
||||
expect(wrapper.find("div.version-pragma__message--ambiguous").length).toEqual(1)
|
||||
expect(wrapper.find("div.version-pragma__message--missing").length).toEqual(0)
|
||||
})
|
||||
it("renders the correct message for a missing-version definition", function(){
|
||||
// When
|
||||
let wrapper = shallow(
|
||||
<VersionPragmaFilter isSwagger2={false} isOAS3={false}>
|
||||
hello!
|
||||
</VersionPragmaFilter>
|
||||
)
|
||||
|
||||
// Then
|
||||
expect(wrapper.find("div.version-pragma__message--missing").length).toEqual(1)
|
||||
expect(wrapper.find("div.version-pragma__message--ambiguous").length).toEqual(0)
|
||||
})
|
||||
|
||||
})
|
||||
@@ -0,0 +1,77 @@
|
||||
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect from "expect"
|
||||
import { mount } from "enzyme"
|
||||
import { fromJS } from "immutable"
|
||||
import ServersContainer from "core/plugins/oas3/components/servers-container"
|
||||
import Servers from "core/plugins/oas3/components/servers"
|
||||
import { Col } from "components/layout-utils"
|
||||
|
||||
describe("<ServersContainer/>", function(){
|
||||
|
||||
const components = {
|
||||
Servers,
|
||||
Col
|
||||
}
|
||||
const mockedProps = {
|
||||
specSelectors: {
|
||||
servers() {}
|
||||
},
|
||||
oas3Selectors: {
|
||||
selectedServer() {},
|
||||
serverVariableValue() {},
|
||||
serverEffectiveValue() {}
|
||||
},
|
||||
oas3Actions: {
|
||||
setSelectedServer() {},
|
||||
setServerVariableValue() {}
|
||||
},
|
||||
getComponent: c => components[c]
|
||||
}
|
||||
|
||||
it("renders Servers inside ServersContainer if servers are provided", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.servers = function() {return fromJS([{url: "http://server1.com"}])}
|
||||
props.oas3Selectors = {...mockedProps.oas3Selectors}
|
||||
props.oas3Selectors.selectedServer = function() {return "http://server1.com"}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<ServersContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedServers = wrapper.find(Servers)
|
||||
expect(renderedServers.length).toEqual(1)
|
||||
})
|
||||
|
||||
it("does not render Servers inside ServersContainer if servers are empty", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
props.specSelectors = {...mockedProps.specSelectors}
|
||||
props.specSelectors.servers = function() {return fromJS([])}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<ServersContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedServers = wrapper.find(Servers)
|
||||
expect(renderedServers.length).toEqual(0)
|
||||
})
|
||||
|
||||
it("does not render Servers inside ServersContainer if servers are undefined", function(){
|
||||
|
||||
// Given
|
||||
let props = {...mockedProps}
|
||||
|
||||
// When
|
||||
let wrapper = mount(<ServersContainer {...props}/>)
|
||||
|
||||
// Then
|
||||
const renderedServers = wrapper.find(Servers)
|
||||
expect(renderedServers.length).toEqual(0)
|
||||
})
|
||||
})
|
||||
@@ -1,7 +1,35 @@
|
||||
import { fromJS } from "immutable"
|
||||
import { createXMLExample, sampleFromSchema } from "corePlugins/samples/fn"
|
||||
import expect from "expect"
|
||||
|
||||
describe("sampleFromSchema", function() {
|
||||
it("handles Immutable.js objects for nested schemas", function () {
|
||||
var definition = fromJS({
|
||||
"type": "object",
|
||||
"properties": {
|
||||
"json": {
|
||||
"type": "object",
|
||||
"example": {
|
||||
"a": "string"
|
||||
},
|
||||
"properties": {
|
||||
"a": {
|
||||
"type": "string"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
})
|
||||
|
||||
var expected = {
|
||||
json: {
|
||||
a: "string"
|
||||
}
|
||||
}
|
||||
|
||||
expect(sampleFromSchema(definition, { includeReadOnly: false })).toEqual(expected)
|
||||
})
|
||||
|
||||
it("returns object with no readonly fields for parameter", function () {
|
||||
var definition = {
|
||||
type: "object",
|
||||
|
||||
@@ -317,7 +317,7 @@ describe("bound system", function(){
|
||||
|
||||
})
|
||||
|
||||
describe("when selector returns a funtcion", function(){
|
||||
describe("when selector returns a function", function(){
|
||||
|
||||
it("should pass the system to that function", function(){
|
||||
|
||||
|
||||
@@ -75,7 +75,7 @@
|
||||
window["SwaggerUIStandalonePreset"] = window["swagger-ui-standalone-preset"]
|
||||
// Build a system
|
||||
const ui = SwaggerUIBundle({
|
||||
url: "http://petstore.swagger.io/v2/swagger.json",
|
||||
url: "https://petstore.swagger.io/v2/swagger.json",
|
||||
dom_id: '#swagger-ui',
|
||||
presets: [
|
||||
SwaggerUIBundle.presets.apis,
|
||||
|
||||
+124
-124
@@ -85,404 +85,404 @@ module.exports = {
|
||||
}
|
||||
},
|
||||
apiWrapper: {
|
||||
selector: ".swagger-ui .wrapper:nth-child(3)",
|
||||
selector: "div.swagger-ui > div:nth-child(2) > div:nth-child(5) > section > div",
|
||||
elements: {
|
||||
petAPIWrapper: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1)"
|
||||
selector: "div.swagger-ui div:nth-child(5) > section > div > span:nth-child(1) > div"
|
||||
},
|
||||
petAPIWrapperBar: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) .opblock-tag"
|
||||
selector: "div.swagger-ui div:nth-child(5) > section > div > span:nth-child(1) > div .opblock-tag"
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Post pet/ api
|
||||
*/
|
||||
petOperationPostContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet"
|
||||
selector: "div#operations-pet-addPet"
|
||||
},
|
||||
petOperationPostTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet .opblock-summary-post span.opblock-summary-path span"
|
||||
selector: "div#operations-pet-addPet .opblock-summary-post span.opblock-summary-path span"
|
||||
},
|
||||
petOperationPostCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet .opblock-summary-post"
|
||||
selector: "div#operations-pet-addPet .opblock-summary-post"
|
||||
},
|
||||
petOperationPostCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet>div:nth-child(2)"
|
||||
selector: "div#operations-pet-addPet>div:nth-child(2)"
|
||||
},
|
||||
petOperationPostTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet button.try-out__btn"
|
||||
selector: "div#operations-pet-addPet button.try-out__btn"
|
||||
},
|
||||
petOperationPostTryText: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet textarea.body-param__text"
|
||||
selector: "div#operations-pet-addPet textarea.body-param__text"
|
||||
},
|
||||
petOperationPostExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet button.execute"
|
||||
selector: "div#operations-pet-addPet button.execute"
|
||||
},
|
||||
petOperationPostTryTextArea: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet textarea"
|
||||
selector: "div#operations-pet-addPet textarea"
|
||||
},
|
||||
petOperationPostResultsBox: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet pre.microlight"
|
||||
selector: "div#operations-pet-addPet pre.microlight"
|
||||
},
|
||||
petOperationPostMockCategoryID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet pre.microlight span:nth-child(17)"
|
||||
selector: "div#operations-pet-addPet pre.microlight span:nth-child(17)"
|
||||
},
|
||||
petOperationPostMockCategoryName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet pre.microlight span:nth-child(23)"
|
||||
selector: "div#operations-pet-addPet pre.microlight span:nth-child(23)"
|
||||
},
|
||||
petOperationPostMockName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet pre.microlight span:nth-child(31)"
|
||||
selector: "div#operations-pet-addPet pre.microlight span:nth-child(31)"
|
||||
},
|
||||
petOperationPostTagID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet pre.microlight span:nth-child(54)"
|
||||
selector: "div#operations-pet-addPet pre.microlight span:nth-child(54)"
|
||||
},
|
||||
petOperationPostTagName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet pre.microlight span:nth-child(60)"
|
||||
selector: "div#operations-pet-addPet pre.microlight span:nth-child(60)"
|
||||
},
|
||||
petOperationPostStatus: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-addPet pre.microlight span:nth-child(70)"
|
||||
selector: "div#operations-pet-addPet pre.microlight span:nth-child(70)"
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Put pet/ api
|
||||
*/
|
||||
petOperationPutContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet"
|
||||
selector: "div#operations-pet-updatePet"
|
||||
},
|
||||
petOperationPutTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet .opblock-summary-put span.opblock-summary-path span"
|
||||
selector: "div#operations-pet-updatePet .opblock-summary-put span.opblock-summary-path span"
|
||||
},
|
||||
petOperationPutCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet .opblock-summary-put"
|
||||
selector: "div#operations-pet-updatePet .opblock-summary-put"
|
||||
},
|
||||
petOperationPutCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet>div:nth-child(2)"
|
||||
selector: "div#operations-pet-updatePet>div:nth-child(2)"
|
||||
},
|
||||
petOperationPutTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet button.try-out__btn"
|
||||
selector: "div#operations-pet-updatePet button.try-out__btn"
|
||||
},
|
||||
petOperationPutTryText: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet textarea.body-param__text"
|
||||
selector: "div#operations-pet-updatePet textarea.body-param__text"
|
||||
},
|
||||
petOperationPutExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet button.execute"
|
||||
selector: "div#operations-pet-updatePet button.execute"
|
||||
},
|
||||
petOperationPutTryTextArea: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet textarea"
|
||||
selector: "div#operations-pet-updatePet textarea"
|
||||
},
|
||||
petOperationPutResultsBox: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet pre.microlight"
|
||||
selector: "div#operations-pet-updatePet pre.microlight"
|
||||
},
|
||||
petOperationPutMockCategoryID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet pre.microlight span:nth-child(17)"
|
||||
selector: "div#operations-pet-updatePet pre.microlight span:nth-child(17)"
|
||||
},
|
||||
petOperationPutMockCategoryName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet pre.microlight span:nth-child(23)"
|
||||
selector: "div#operations-pet-updatePet pre.microlight span:nth-child(23)"
|
||||
},
|
||||
petOperationPutMockName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet pre.microlight span:nth-child(31)"
|
||||
selector: "div#operations-pet-updatePet pre.microlight span:nth-child(31)"
|
||||
},
|
||||
petOperationPutTagID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet pre.microlight span:nth-child(54)"
|
||||
selector: "div#operations-pet-updatePet pre.microlight span:nth-child(54)"
|
||||
},
|
||||
petOperationPutTagName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet pre.microlight span:nth-child(60)"
|
||||
selector: "div#operations-pet-updatePet pre.microlight span:nth-child(60)"
|
||||
},
|
||||
petOperationPutStatus: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-updatePet pre.microlight span:nth-child(70)"
|
||||
selector: "div#operations-pet-updatePet pre.microlight span:nth-child(70)"
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Get /pet/findByTags
|
||||
*/
|
||||
petOperationGetByTagContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags"
|
||||
selector: "div#operations-pet-findPetsByTags"
|
||||
},
|
||||
petOperationGetByTagTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags .opblock-summary-get span.opblock-summary-path__deprecated span"
|
||||
selector: "div#operations-pet-findPetsByTags .opblock-summary-get span.opblock-summary-path__deprecated span"
|
||||
},
|
||||
petOperationGetByTagCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags .opblock-summary-get"
|
||||
selector: "div#operations-pet-findPetsByTags .opblock-summary-get"
|
||||
},
|
||||
petOperationGetByTagCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags .ReactCollapse--collapse"
|
||||
selector: "div#operations-pet-findPetsByTags .ReactCollapse--collapse"
|
||||
},
|
||||
petOperationGetByTagTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags button.try-out__btn"
|
||||
selector: "div#operations-pet-findPetsByTags button.try-out__btn"
|
||||
},
|
||||
petOperationGetByTagTryAdded: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags button.json-schema-form-item-add"
|
||||
selector: "div#operations-pet-findPetsByTags button.json-schema-form-item-add"
|
||||
},
|
||||
petOperationGetByTagExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags button.execute"
|
||||
selector: "div#operations-pet-findPetsByTags button.execute"
|
||||
},
|
||||
petOperationGetByTagTryTextArea: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags textarea"
|
||||
selector: "div#operations-pet-findPetsByTags textarea"
|
||||
},
|
||||
petOperationGetByTagResultsBox: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags pre.microlight"
|
||||
selector: "div#operations-pet-findPetsByTags pre.microlight"
|
||||
},
|
||||
petOperationGetByTagMockCategoryID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags pre.microlight span:nth-child(17)"
|
||||
selector: "div#operations-pet-findPetsByTags pre.microlight span:nth-child(17)"
|
||||
},
|
||||
petOperationGetByTagMockCategoryName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags pre.microlight span:nth-child(23)"
|
||||
selector: "div#operations-pet-findPetsByTags pre.microlight span:nth-child(23)"
|
||||
},
|
||||
petOperationGetByTagMockName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags pre.microlight span:nth-child(31)"
|
||||
selector: "div#operations-pet-findPetsByTags pre.microlight span:nth-child(31)"
|
||||
},
|
||||
petOperationGetByTagTagID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags pre.microlight span:nth-child(54)"
|
||||
selector: "div#operations-pet-findPetsByTags pre.microlight span:nth-child(54)"
|
||||
},
|
||||
petOperationGetByTagTagName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags pre.microlight span:nth-child(60)"
|
||||
selector: "div#operations-pet-findPetsByTags pre.microlight span:nth-child(60)"
|
||||
},
|
||||
petOperationGetByTagStatus: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-findPetsByTags pre.microlight span:nth-child(70)"
|
||||
selector: "div#operations-pet-findPetsByTags pre.microlight span:nth-child(70)"
|
||||
},
|
||||
|
||||
/**
|
||||
* Get /pet/{petId}
|
||||
*/
|
||||
petOperationGetByIdContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-getPetById"
|
||||
selector: "div#operations-pet-getPetById"
|
||||
},
|
||||
petOperationGetByIdTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-getPetById .opblock-summary-get span.opblock-summary-path span"
|
||||
selector: "div#operations-pet-getPetById .opblock-summary-get span.opblock-summary-path span"
|
||||
},
|
||||
petOperationGetByIdCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-getPetById .opblock-summary-get"
|
||||
selector: "div#operations-pet-getPetById .opblock-summary-get"
|
||||
},
|
||||
petOperationGetByIdCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-getPetById .ReactCollapse--collapse"
|
||||
selector: "div#operations-pet-getPetById .ReactCollapse--collapse"
|
||||
},
|
||||
petOperationGetByIdTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-getPetById button.try-out__btn"
|
||||
selector: "div#operations-pet-getPetById button.try-out__btn"
|
||||
},
|
||||
petOperationGetByIdExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-getPetById button.execute"
|
||||
selector: "div#operations-pet-getPetById button.execute"
|
||||
},
|
||||
petOperationGetByIdParameter: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-pet-getPetById div.parameters-col_description input"
|
||||
},
|
||||
selector: "div#operations-pet-getPetById div.parameters-col_description input"
|
||||
},
|
||||
petOperationGetByIdResultsBox: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-getPetById pre.microlight"
|
||||
},
|
||||
|
||||
selector: "div#operations-pet-getPetById pre.microlight"
|
||||
},
|
||||
|
||||
/**
|
||||
* Delete pet/
|
||||
*/
|
||||
petOperationDeleteContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet"
|
||||
selector: "div#operations-pet-deletePet"
|
||||
},
|
||||
petOperationDeleteTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet .opblock-summary-delete span.opblock-summary-path span"
|
||||
selector: "div#operations-pet-deletePet .opblock-summary-delete span.opblock-summary-path span"
|
||||
},
|
||||
petOperationDeleteCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet .opblock-summary-delete"
|
||||
selector: "div#operations-pet-deletePet .opblock-summary-delete"
|
||||
},
|
||||
petOperationDeleteCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet>div:nth-child(2)"
|
||||
selector: "div#operations-pet-deletePet>div:nth-child(2)"
|
||||
},
|
||||
petOperationDeleteTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet button.try-out__btn"
|
||||
selector: "div#operations-pet-deletePet button.try-out__btn"
|
||||
},
|
||||
petOperationDeleteExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet button.execute"
|
||||
selector: "div#operations-pet-deletePet button.execute"
|
||||
},
|
||||
petOperationDeleteTryTextArea: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet textarea"
|
||||
selector: "div#operations-pet-deletePet textarea"
|
||||
},
|
||||
petOperationDeleteResultsBox: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet pre.microlight"
|
||||
selector: "div#operations-pet-deletePet pre.microlight"
|
||||
},
|
||||
petOperationDeleteMockCategoryID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet pre.microlight span:nth-child(17)"
|
||||
selector: "div#operations-pet-deletePet pre.microlight span:nth-child(17)"
|
||||
},
|
||||
petOperationDeleteMockCategoryName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet pre.microlight span:nth-child(23)"
|
||||
selector: "div#operations-pet-deletePet pre.microlight span:nth-child(23)"
|
||||
},
|
||||
petOperationDeleteMockName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet pre.microlight span:nth-child(31)"
|
||||
selector: "div#operations-pet-deletePet pre.microlight span:nth-child(31)"
|
||||
},
|
||||
petOperationDeleteTagID: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet pre.microlight span:nth-child(54)"
|
||||
selector: "div#operations-pet-deletePet pre.microlight span:nth-child(54)"
|
||||
},
|
||||
petOperationDeleteTagName: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet pre.microlight span:nth-child(60)"
|
||||
selector: "div#operations-pet-deletePet pre.microlight span:nth-child(60)"
|
||||
},
|
||||
petOperationDeleteStatus: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(1) div#operations-pet-deletePet pre.microlight span:nth-child(70)"
|
||||
selector: "div#operations-pet-deletePet pre.microlight span:nth-child(70)"
|
||||
},
|
||||
|
||||
/**
|
||||
* ***********Store************
|
||||
*/
|
||||
storeAPIWrapper: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2)"
|
||||
selector: "div.swagger-ui div:nth-child(5) > section > div > span:nth-child(2) > div"
|
||||
},
|
||||
storeAPIWrapperBar: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) .opblock-tag"
|
||||
selector: "div.swagger-ui div:nth-child(5) > section > div > span:nth-child(2) > div .opblock-tag"
|
||||
},
|
||||
/**
|
||||
* Get /store/inventory
|
||||
*/
|
||||
storeOperationGetContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory"
|
||||
selector: "div#operations-store-getInventory"
|
||||
},
|
||||
storeOperationGetTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory .opblock-summary-get span.opblock-summary-path span"
|
||||
selector: "div#operations-store-getInventory .opblock-summary-get span.opblock-summary-path span"
|
||||
},
|
||||
storeOperationGetCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory .opblock-summary-get"
|
||||
selector: "div#operations-store-getInventory .opblock-summary-get"
|
||||
},
|
||||
storeOperationGetCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory>div:nth-child(2)"
|
||||
selector: "div#operations-store-getInventory>div:nth-child(2)"
|
||||
},
|
||||
storeOperationGetTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory button.try-out__btn"
|
||||
selector: "div#operations-store-getInventory button.try-out__btn"
|
||||
},
|
||||
storeOperationGetExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory button.execute"
|
||||
selector: "div#operations-store-getInventory button.execute"
|
||||
},
|
||||
storeOperationResponseProps1: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory pre.example.microlight span:nth-child(6)"
|
||||
selector: "div#operations-store-getInventory pre.example.microlight span:nth-child(6)"
|
||||
},
|
||||
storeOperationResponseProps2: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory pre.example.microlight span:nth-child(12)"
|
||||
selector: "div#operations-store-getInventory pre.example.microlight span:nth-child(12)"
|
||||
},
|
||||
storeOperationResponseProps3: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-getInventory pre.example.microlight span:nth-child(18)"
|
||||
selector: "div#operations-store-getInventory pre.example.microlight span:nth-child(18)"
|
||||
},
|
||||
/**
|
||||
* Post /store/order
|
||||
*/
|
||||
storeOperationPostContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder"
|
||||
selector: "div#operations-store-placeOrder"
|
||||
},
|
||||
storeOperationPostTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder .opblock-summary-post span.opblock-summary-path span"
|
||||
selector: "div#operations-store-placeOrder .opblock-summary-post span.opblock-summary-path span"
|
||||
},
|
||||
storeOperationPostCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder .opblock-summary-post"
|
||||
selector: "div#operations-store-placeOrder .opblock-summary-post"
|
||||
},
|
||||
storeOperationPostCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder>div:nth-child(2)"
|
||||
selector: "div#operations-store-placeOrder>div:nth-child(2)"
|
||||
},
|
||||
storeOperationPostTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder button.try-out__btn"
|
||||
selector: "div#operations-store-placeOrder button.try-out__btn"
|
||||
},
|
||||
storeOperationPostExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder button.execute"
|
||||
selector: "div#operations-store-placeOrder button.execute"
|
||||
},
|
||||
storeOperationPostResponseId: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder pre.example.microlight span:nth-child(22)"
|
||||
selector: "div#operations-store-placeOrder pre.example.microlight span:nth-child(22)"
|
||||
},
|
||||
storeOperationPostResponsePetId: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder pre.example.microlight span:nth-child(31)"
|
||||
selector: "div#operations-store-placeOrder pre.example.microlight span:nth-child(31)"
|
||||
},
|
||||
storeOperationPostResponseQuantity: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder pre.example.microlight span:nth-child(40)"
|
||||
selector: "div#operations-store-placeOrder pre.example.microlight span:nth-child(40)"
|
||||
},
|
||||
storeOperationPostResponseStatus: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder pre.example.microlight span:nth-child(66)"
|
||||
selector: "div#operations-store-placeOrder pre.example.microlight span:nth-child(66)"
|
||||
},
|
||||
storeOperationPostResponseComplete: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-placeOrder pre.example.microlight span:nth-child(75)"
|
||||
selector: "div#operations-store-placeOrder pre.example.microlight span:nth-child(75)"
|
||||
},
|
||||
/**
|
||||
* Delete /store/order/{orderId}
|
||||
*/
|
||||
storeOperationDeleteContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-deleteOrder"
|
||||
selector: "div#operations-store-deleteOrder"
|
||||
},
|
||||
storeOperationDeleteTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-deleteOrder .opblock-summary-delete span.opblock-summary-path span"
|
||||
selector: "div#operations-store-deleteOrder .opblock-summary-delete span.opblock-summary-path span"
|
||||
},
|
||||
storeOperationDeleteCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-deleteOrder .opblock-summary-delete"
|
||||
selector: "div#operations-store-deleteOrder .opblock-summary-delete"
|
||||
},
|
||||
storeOperationDeleteCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-deleteOrder>div:nth-child(2)"
|
||||
selector: "div#operations-store-deleteOrder>div:nth-child(2)"
|
||||
},
|
||||
storeOperationDeleteTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-deleteOrder button.try-out__btn"
|
||||
selector: "div#operations-store-deleteOrder button.try-out__btn"
|
||||
},
|
||||
storeOperationDeleteExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-deleteOrder button.execute"
|
||||
selector: "div#operations-store-deleteOrder button.execute"
|
||||
},
|
||||
storeOperationGetResponseHeaders: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(2) div#operations-store-deleteOrder pre span"
|
||||
selector: "div#operations-store-deleteOrder pre span"
|
||||
},
|
||||
/**
|
||||
* *********User**************
|
||||
*/
|
||||
userAPIWrapper: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3)"
|
||||
selector: "div.swagger-ui div:nth-child(5) > section > div > span:nth-child(3) > div"
|
||||
},
|
||||
userAPIWrapperBar: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) .opblock-tag"
|
||||
selector: "div.swagger-ui div:nth-child(5) > section > div > span:nth-child(3) > div .opblock-tag"
|
||||
},
|
||||
/**
|
||||
* Put /user/login
|
||||
*/
|
||||
userOperationPutContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser"
|
||||
selector: "div#operations-user-updateUser"
|
||||
},
|
||||
userOperationPutTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser .opblock-summary-put span.opblock-summary-path span"
|
||||
selector: "div#operations-user-updateUser .opblock-summary-put span.opblock-summary-path span"
|
||||
},
|
||||
userOperationPutCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser .opblock-summary-put"
|
||||
selector: "div#operations-user-updateUser .opblock-summary-put"
|
||||
},
|
||||
userOperationPutCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser>div:nth-child(2)"
|
||||
selector: "div#operations-user-updateUser>div:nth-child(2)"
|
||||
},
|
||||
userOperationPutTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser button.try-out__btn"
|
||||
selector: "div#operations-user-updateUser button.try-out__btn"
|
||||
},
|
||||
userOperationPutExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser button.execute"
|
||||
selector: "div#operations-user-updateUser button.execute"
|
||||
},
|
||||
userOperationPutParameter: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser div.parameters-col_description input"
|
||||
selector: "div#operations-user-updateUser div.parameters-col_description input"
|
||||
},
|
||||
userOperationPutResponseHeader: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-updateUser div.parameters-col_description input"
|
||||
selector: "div#operations-user-updateUser div.parameters-col_description input"
|
||||
},
|
||||
/**
|
||||
* Delete /user
|
||||
*/
|
||||
userOperationDeleteContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-deleteUser"
|
||||
selector: "div#operations-user-deleteUser"
|
||||
},
|
||||
userOperationDeleteTitle: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-deleteUser .opblock-summary-delete span.opblock-summary-path span"
|
||||
selector: "div#operations-user-deleteUser .opblock-summary-delete span.opblock-summary-path span"
|
||||
},
|
||||
userOperationDeleteCollpase: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-deleteUser .opblock-summary-delete"
|
||||
selector: "div#operations-user-deleteUser .opblock-summary-delete"
|
||||
},
|
||||
userOperationDeleteCollapseContainer: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-deleteUser>div:nth-child(2)"
|
||||
selector: "div#operations-user-deleteUser>div:nth-child(2)"
|
||||
},
|
||||
userOperationDeleteTryBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-deleteUser button.try-out__btn"
|
||||
selector: "div#operations-user-deleteUser button.try-out__btn"
|
||||
},
|
||||
userOperationDeleteExecuteBtn: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-deleteUser button.execute"
|
||||
selector: "div#operations-user-deleteUser button.execute"
|
||||
},
|
||||
userOperationDeleteParameter: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) div#operations-user-deleteUser div.parameters-col_description input"
|
||||
selector: "div#operations-user-deleteUser div.parameters-col_description input"
|
||||
},
|
||||
userOperationDeleteResponseHeader: {
|
||||
selector: ".swagger-ui .opblock-tag-section:nth-child(3) .opblock-delete div.parameters-col_description input"
|
||||
selector: "div#operations-user-deleteUser div.parameters-col_description input"
|
||||
},
|
||||
|
||||
}
|
||||
},
|
||||
/* Model Container */
|
||||
modelWrapper: {
|
||||
selector: ".swagger-ui .wrapper:nth-child(4)",
|
||||
selector: "div.swagger-ui > div:nth-child(2) > div:nth-child(6)",
|
||||
elements: {
|
||||
modelContainer: {
|
||||
selector: ".swagger-ui .models"
|
||||
|
||||
Reference in New Issue
Block a user