Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
b873ee78d4 | ||
|
|
2c86cd5820 | ||
|
|
7de652de0b | ||
|
|
897362a301 | ||
|
|
7c195f0f35 | ||
|
|
a03bcbdaf4 | ||
|
|
80de498ca4 | ||
|
|
8dab91f184 | ||
|
|
4705502efb | ||
|
|
6815f1d7bb | ||
|
|
6cf6a85637 | ||
|
|
98b36bdbd2 | ||
|
|
18a681e231 | ||
|
|
537b6d88b5 | ||
|
|
3ac24da271 | ||
|
|
7c8942e61c | ||
|
|
0103364880 | ||
|
|
7344315c34 | ||
|
|
a0f8f9a05d | ||
|
|
13f888999f | ||
|
|
f32492b4ee | ||
|
|
5659b2c8eb | ||
|
|
2cd4989c05 | ||
|
|
1e146627d2 | ||
|
|
37aead915e | ||
|
|
74165f5292 | ||
|
|
f11ab532e8 | ||
|
|
60e8091eed | ||
|
|
1785d48746 | ||
|
|
a5763a56cc | ||
|
|
13aa95ff00 | ||
|
|
ec76e512e2 | ||
|
|
729fd71546 | ||
|
|
fa24b6aec8 | ||
|
|
2f59c4a5f4 | ||
|
|
d32fe02713 | ||
|
|
446bda369c | ||
|
|
8354132915 | ||
|
|
ca28c8c8d6 | ||
|
|
de231c0325 | ||
|
|
5a69603beb | ||
|
|
559b315d0d |
@@ -6,7 +6,7 @@
|
||||
|
||||
**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 contribution](https://github.com/swagger-api/swagger-ui/issues?q=is%3Aissue+is%3Aopen+label%3A%22Good+first+contribution%22) label.
|
||||
**👉🏼 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.
|
||||
|
||||
@@ -22,7 +22,7 @@ The OpenAPI Specification has undergone 5 revisions since initial creation in 20
|
||||
|
||||
Swagger UI Version | Release Date | OpenAPI Spec compatibility | Notes
|
||||
------------------ | ------------ | -------------------------- | -----
|
||||
3.3.0 | 2017-09-29 | 2.0, 3.0 | [tag v3.3.0](https://github.com/swagger-api/swagger-ui/tree/v3.3.0)
|
||||
3.3.2 | 2017-10-13 | 2.0, 3.0 | [tag v3.3.2](https://github.com/swagger-api/swagger-ui/tree/v3.3.2)
|
||||
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)
|
||||
@@ -119,7 +119,7 @@ scopeSeparator | scope separator for passing scopes, encoded before calling, def
|
||||
additionalQueryStringParams | Additional query parameters added to `authorizationUrl` and `tokenUrl`. MUST be an object
|
||||
useBasicAuthenticationWithAccessCodeGrant | Only activated for the `accessCode` flow. During the `authorization_code` request to the `tokenUrl`, pass the [Client Password](https://tools.ietf.org/html/rfc6749#section-2.3.1) using the HTTP Basic Authentication scheme (`Authorization` header with `Basic base64encoded[client_id:client_secret]`). The default is `false`
|
||||
|
||||
```
|
||||
```javascript
|
||||
const ui = SwaggerUIBundle({...})
|
||||
|
||||
// Method can be called in any place after calling constructor SwaggerUIBundle
|
||||
@@ -171,7 +171,7 @@ showMutatedRequest | If set to `true` (the default), uses the mutated request re
|
||||
#### Topbar plugin
|
||||
Topbar plugin enables top bar with input for spec path and explore button or a dropdown if `urls` is used. By default the plugin is enabled, and to disable it you need to remove Topbar plugin from presets in `src/standalone/index.js`:
|
||||
|
||||
```
|
||||
```javascript
|
||||
let preset = [
|
||||
// TopbarPlugin,
|
||||
ConfigsPlugin,
|
||||
|
||||
Vendored
+18
-18
File diff suppressed because one or more lines are too long
Vendored
+1
-1
@@ -1 +1 @@
|
||||
{"version":3,"file":"swagger-ui-bundle.js","sources":["webpack:///swagger-ui-bundle.js"],"mappings":"AAAA;;;;;AAonMA;;;;;;AAm5DA;;;;;;;;;;;;;;;;;;;;;;;;;;AAukUA;;;;;;;;;;;;;;AAq4JA;AAw+iBA;;;;;;;;;AA8oIA;;;;;AA87QA;;;;;AAynBA;AAo0CA;;;;;;AA6gZA;;;;;;AAkzZA;AAixYA","sourceRoot":""}
|
||||
{"version":3,"file":"swagger-ui-bundle.js","sources":["webpack:///swagger-ui-bundle.js"],"mappings":"AAAA;;;;;AAsnMA;;;;;;AAm5DA;;;;;;;;;;;;;;;;;;;;;;;;;;AA0kUA;;;;;;;;;;;;;;AAq4JA;AA4/iBA;;;;;;;;;AA+vIA;;;;;AAk8QA;;;;;AAynBA;AAo0CA;;;;;;AAuqxBA;AAixYA;;;;;;AA6gbA","sourceRoot":""}
|
||||
Vendored
+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
+1
-1
@@ -1 +1 @@
|
||||
{"version":3,"file":"swagger-ui.js","sources":["webpack:///swagger-ui.js"],"mappings":"AAAA;;;;;;AAy7eA","sourceRoot":""}
|
||||
{"version":3,"file":"swagger-ui.js","sources":["webpack:///swagger-ui.js"],"mappings":"AAAA;;;;;;AAs9eA","sourceRoot":""}
|
||||
+3
-3
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "swagger-ui",
|
||||
"version": "3.3.0",
|
||||
"version": "3.3.2",
|
||||
"main": "dist/swagger-ui.js",
|
||||
"repository": "git@github.com:swagger-api/swagger-ui.git",
|
||||
"contributors": [
|
||||
@@ -32,7 +32,7 @@
|
||||
"test": "npm run lint-errors && npm run just-test-in-node",
|
||||
"test-in-node": "npm run lint-errors && npm run just-test-in-node",
|
||||
"just-test": "karma start --config karma.conf.js",
|
||||
"just-test-in-node": "mocha --recursive --compilers js:babel-core/register test/core test/components test/bugs test/swagger-ui-dist-package",
|
||||
"just-test-in-node": "mocha --recursive --compilers js:babel-core/register test/core test/components test/bugs test/swagger-ui-dist-package test/xss",
|
||||
"test-e2e": "sleep 3 && nightwatch test/e2e/scenarios/ --config test/e2e/nightwatch.json",
|
||||
"e2e-initial-render": "nightwatch test/e2e/scenarios/ --config test/e2e/nightwatch.json --group initial-render",
|
||||
"mock-api": "json-server --watch test/e2e/db.json --port 3204",
|
||||
@@ -78,7 +78,7 @@
|
||||
"scroll-to-element": "^2.0.0",
|
||||
"serialize-error": "2.0.0",
|
||||
"shallowequal": "0.2.2",
|
||||
"swagger-client": "^3.2.0",
|
||||
"swagger-client": "^3.2.2",
|
||||
"url-parse": "^1.1.8",
|
||||
"whatwg-fetch": "0.11.1",
|
||||
"worker-loader": "^0.7.1",
|
||||
|
||||
@@ -29,7 +29,10 @@ Markdown.propTypes = {
|
||||
export default Markdown
|
||||
|
||||
const sanitizeOptions = {
|
||||
allowedTags: sanitize.defaults.allowedTags.concat([ "img" ]),
|
||||
allowedTags: sanitize.defaults.allowedTags.concat([ "h1", "h2", "img" ]),
|
||||
allowedAttributes: {
|
||||
"img": sanitize.defaults.allowedAttributes.img.concat(["title"])
|
||||
},
|
||||
textFilter: function(text) {
|
||||
return text.replace(/"/g, "\"")
|
||||
}
|
||||
|
||||
@@ -83,8 +83,12 @@ export default class ResponseBody extends React.Component {
|
||||
// Anything else (CORS)
|
||||
} else if (typeof content === "string") {
|
||||
bodyEl = <HighlightCode value={ content } />
|
||||
} else {
|
||||
} else if ( content.size > 0 ) {
|
||||
// We don't know the contentType, but there was some content returned
|
||||
bodyEl = <div>Unknown response type</div>
|
||||
} else {
|
||||
// We don't know the contentType and there was no content returned
|
||||
bodyEl = null
|
||||
}
|
||||
|
||||
return ( !bodyEl ? null : <div>
|
||||
|
||||
@@ -10,7 +10,7 @@ export const shownDefinitions = createSelector(
|
||||
|
||||
export const definitionsToAuthorize = createSelector(
|
||||
state,
|
||||
() =>( { specSelectors } ) => {
|
||||
() => ( { specSelectors } ) => {
|
||||
let definitions = specSelectors.securityDefinitions()
|
||||
let list = List()
|
||||
|
||||
@@ -27,7 +27,7 @@ export const definitionsToAuthorize = createSelector(
|
||||
)
|
||||
|
||||
|
||||
export const getDefinitionsByNames = ( state, securities ) =>( { specSelectors } ) => {
|
||||
export const getDefinitionsByNames = ( state, securities ) => ( { specSelectors } ) => {
|
||||
let securityDefinitions = specSelectors.securityDefinitions()
|
||||
let result = List()
|
||||
|
||||
@@ -64,7 +64,7 @@ export const authorized = createSelector(
|
||||
)
|
||||
|
||||
|
||||
export const isAuthorized = ( state, securities ) =>( { authSelectors } ) => {
|
||||
export const isAuthorized = ( state, securities ) => ( { authSelectors } ) => {
|
||||
let authorized = authSelectors.authorized()
|
||||
|
||||
if(!List.isList(securities)) {
|
||||
|
||||
@@ -7,13 +7,16 @@ export default function downloadUrlPlugin (toolbox) {
|
||||
let { fn } = toolbox
|
||||
|
||||
const actions = {
|
||||
download: (url)=> ({ errActions, specSelectors, specActions }) => {
|
||||
download: (url)=> ({ errActions, specSelectors, specActions, getConfigs }) => {
|
||||
let { fetch } = fn
|
||||
const config = getConfigs()
|
||||
url = url || specSelectors.url()
|
||||
specActions.updateLoadingStatus("loading")
|
||||
fetch({
|
||||
url,
|
||||
loadSpec: true,
|
||||
requestInterceptor: config.requestInterceptor || (a => a),
|
||||
responseInterceptor: config.responseInterceptor || (a => a),
|
||||
credentials: "same-origin",
|
||||
headers: {
|
||||
"Accept": "application/json,*/*"
|
||||
|
||||
@@ -1,11 +1,12 @@
|
||||
import { createSelector } from "reselect"
|
||||
import { List } from "immutable"
|
||||
import { isOAS3 as isOAS3Helper } from "../helpers"
|
||||
|
||||
|
||||
// Helpers
|
||||
|
||||
function onlyOAS3(selector) {
|
||||
return (ori, system) => (...args) => {
|
||||
return (ori, system) => (state, ...args) => {
|
||||
const spec = system.getSystem().specSelectors.specJson()
|
||||
if(isOAS3Helper(spec)) {
|
||||
return selector(...args)
|
||||
@@ -19,10 +20,10 @@ const nullSelector = createSelector(() => null)
|
||||
|
||||
const OAS3NullSelector = onlyOAS3(nullSelector)
|
||||
|
||||
// Hasta la vista, authentication!
|
||||
// Hasta la vista, authorization!
|
||||
export const shownDefinitions = OAS3NullSelector
|
||||
export const definitionsToAuthorize = OAS3NullSelector
|
||||
export const getDefinitionsByNames = OAS3NullSelector
|
||||
export const authorized = OAS3NullSelector
|
||||
export const authorized = onlyOAS3(() => List())
|
||||
export const isAuthorized = OAS3NullSelector
|
||||
export const getConfigs = OAS3NullSelector
|
||||
|
||||
@@ -6,6 +6,7 @@ import { OrderedMap } from "immutable"
|
||||
const RequestBody = ({
|
||||
requestBody,
|
||||
getComponent,
|
||||
getConfigs,
|
||||
specSelectors,
|
||||
contentType,
|
||||
isExecute,
|
||||
@@ -27,6 +28,7 @@ const RequestBody = ({
|
||||
}
|
||||
<ModelExample
|
||||
getComponent={ getComponent }
|
||||
getConfigs={ getConfigs }
|
||||
specSelectors={ specSelectors }
|
||||
expandDepth={1}
|
||||
isExecute={isExecute}
|
||||
@@ -46,6 +48,7 @@ const RequestBody = ({
|
||||
RequestBody.propTypes = {
|
||||
requestBody: ImPropTypes.orderedMap.isRequired,
|
||||
getComponent: PropTypes.func.isRequired,
|
||||
getConfigs: PropTypes.func.isRequired,
|
||||
specSelectors: PropTypes.object.isRequired,
|
||||
contentType: PropTypes.string.isRequired,
|
||||
isExecute: PropTypes.bool.isRequired,
|
||||
|
||||
@@ -1,10 +1,11 @@
|
||||
import React from "react"
|
||||
import PropTypes from "prop-types"
|
||||
import ReactMarkdown from "react-markdown"
|
||||
import { Parser, HtmlRenderer } from "commonmark"
|
||||
import { OAS3ComponentWrapFactory } from "../helpers"
|
||||
import { sanitizer } from "core/components/providers/markdown"
|
||||
|
||||
export default OAS3ComponentWrapFactory(({ source }) => {
|
||||
export const Markdown = ({ source }) => {
|
||||
if ( source ) {
|
||||
const parser = new Parser()
|
||||
const writer = new HtmlRenderer()
|
||||
@@ -23,4 +24,9 @@ export default OAS3ComponentWrapFactory(({ source }) => {
|
||||
)
|
||||
}
|
||||
return null
|
||||
})
|
||||
}
|
||||
Markdown.propTypes = {
|
||||
source: PropTypes.string
|
||||
}
|
||||
|
||||
export default OAS3ComponentWrapFactory(Markdown)
|
||||
@@ -137,10 +137,13 @@ export function changeParam( path, paramName, paramIn, value, isXml ){
|
||||
}
|
||||
}
|
||||
|
||||
export function validateParams( payload ){
|
||||
export const validateParams = ( payload, isOAS3 ) =>{
|
||||
return {
|
||||
type: VALIDATE_PARAMS,
|
||||
payload:{ pathMethod: payload }
|
||||
payload:{
|
||||
pathMethod: payload,
|
||||
isOAS3
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -51,14 +51,14 @@ export default {
|
||||
})
|
||||
},
|
||||
|
||||
[VALIDATE_PARAMS]: ( state, { payload: { pathMethod } } ) => {
|
||||
[VALIDATE_PARAMS]: ( state, { payload: { pathMethod, isOAS3 } } ) => {
|
||||
let operation = state.getIn( [ "resolved", "paths", ...pathMethod ] )
|
||||
let isXml = /xml/i.test(operation.get("consumes_value"))
|
||||
|
||||
return state.updateIn( [ "resolved", "paths", ...pathMethod, "parameters" ], fromJS([]), parameters => {
|
||||
return parameters.withMutations( parameters => {
|
||||
for ( let i = 0, len = parameters.count(); i < len; i++ ) {
|
||||
let errors = validateParam(parameters.get(i), isXml)
|
||||
let errors = validateParam(parameters.get(i), isXml, isOAS3)
|
||||
parameters.setIn([i, "errors"], fromJS(errors))
|
||||
}
|
||||
})
|
||||
|
||||
@@ -13,3 +13,7 @@ export const executeRequest = (ori, { specActions }) => (req) => {
|
||||
specActions.logRequest(req)
|
||||
return ori(req)
|
||||
}
|
||||
|
||||
export const validateParams = (ori, { specSelectors }) => (req) => {
|
||||
return ori(req, specSelectors.isOAS3())
|
||||
}
|
||||
+10
-8
@@ -537,16 +537,18 @@ export const validateMinLength = (val, min) => {
|
||||
}
|
||||
|
||||
// validation of parameters before execute
|
||||
export const validateParam = (param, isXml) => {
|
||||
export const validateParam = (param, isXml, isOAS3 = false) => {
|
||||
let errors = []
|
||||
let value = isXml && param.get("in") === "body" ? param.get("value_xml") : param.get("value")
|
||||
let required = param.get("required")
|
||||
let maximum = param.get("maximum")
|
||||
let minimum = param.get("minimum")
|
||||
let type = param.get("type")
|
||||
let format = param.get("format")
|
||||
let maxLength = param.get("maxLength")
|
||||
let minLength = param.get("minLength")
|
||||
|
||||
let paramDetails = isOAS3 ? param.get("schema") : param
|
||||
let maximum = paramDetails.get("maximum")
|
||||
let minimum = paramDetails.get("minimum")
|
||||
let type = paramDetails.get("type")
|
||||
let format = paramDetails.get("format")
|
||||
let maxLength = paramDetails.get("maxLength")
|
||||
let minLength = paramDetails.get("minLength")
|
||||
|
||||
/*
|
||||
If the parameter is required OR the parameter has a value (meaning optional, but filled in)
|
||||
@@ -616,7 +618,7 @@ export const validateParam = (param, isXml) => {
|
||||
|
||||
if ( !value.count() ) { return errors }
|
||||
|
||||
itemType = param.getIn(["items", "type"])
|
||||
itemType = paramDetails.getIn(["items", "type"])
|
||||
|
||||
value.forEach((item, index) => {
|
||||
let err
|
||||
|
||||
@@ -543,14 +543,14 @@
|
||||
|
||||
.response-col_description__inner
|
||||
{
|
||||
span
|
||||
div.markdown, div.renderedMarkdown
|
||||
{
|
||||
font-size: 12px;
|
||||
font-style: italic;
|
||||
|
||||
display: block;
|
||||
|
||||
margin: 10px 0;
|
||||
margin: 0;
|
||||
padding: 10px;
|
||||
|
||||
border-radius: 4px;
|
||||
|
||||
@@ -0,0 +1,48 @@
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect from "expect"
|
||||
import { render } from "enzyme"
|
||||
import Markdown from "components/providers/markdown"
|
||||
import { Markdown as OAS3Markdown } from "corePlugins/oas3/wrap-components/markdown.js"
|
||||
|
||||
describe("Markdown component", function() {
|
||||
describe("Swagger 2.0", function() {
|
||||
it("allows image elements", function() {
|
||||
const str = ``
|
||||
const el = render(<Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="markdown"><p><img src="http://image.source" title="Image title"></p>\n</div>`)
|
||||
})
|
||||
|
||||
it("allows heading elements", function() {
|
||||
const str = `
|
||||
# h1
|
||||
## h2
|
||||
### h3
|
||||
#### h4
|
||||
##### h5
|
||||
###### h6`
|
||||
const el = render(<Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="markdown"><h1>h1</h1>\n<h2>h2</h2>\n<h3>h3</h3>\n<h4>h4</h4>\n<h5>h5</h5>\n<h6>h6</h6>\n</div>`)
|
||||
})
|
||||
})
|
||||
|
||||
describe("OAS 3", function() {
|
||||
it("allows image elements", function() {
|
||||
const str = ``
|
||||
const el = render(<OAS3Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="renderedMarkdown"><div><p><img src="http://image.source" title="Image title"></p></div></div>`)
|
||||
})
|
||||
|
||||
it("allows heading elements", function() {
|
||||
const str = `
|
||||
# h1
|
||||
## h2
|
||||
### h3
|
||||
#### h4
|
||||
##### h5
|
||||
###### h6`
|
||||
const el = render(<OAS3Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="renderedMarkdown"><div><h1>h1</h1>\n<h2>h2</h2>\n<h3>h3</h3>\n<h4>h4</h4>\n<h5>h5</h5>\n<h6>h6</h6></div></div>`)
|
||||
})
|
||||
})
|
||||
})
|
||||
+160
-183
@@ -277,461 +277,438 @@ describe("utils", function() {
|
||||
let param = null
|
||||
let result = null
|
||||
|
||||
it("skips validation when `type` is not specified", function() {
|
||||
// invalid type
|
||||
const assertValidateParam = (param, expectedError) => {
|
||||
// Swagger 2.0 version
|
||||
result = validateParam( fromJS(param), false )
|
||||
expect( result ).toEqual( expectedError )
|
||||
|
||||
// OAS3 version, using `schema` sub-object
|
||||
let oas3Param = {
|
||||
value: param.value,
|
||||
required: param.required,
|
||||
schema: {
|
||||
...param,
|
||||
value: undefined,
|
||||
required: undefined
|
||||
}
|
||||
}
|
||||
result = validateParam( fromJS(oas3Param), false, true )
|
||||
expect( result ).toEqual( expectedError )
|
||||
}
|
||||
|
||||
it("should check the isOAS3 flag when validating parameters", function() {
|
||||
// This should "skip" validation because there is no `schema.type` property
|
||||
// and we are telling `validateParam` this is an OAS3 spec
|
||||
param = fromJS({
|
||||
required: false,
|
||||
type: undefined,
|
||||
value: ""
|
||||
value: "",
|
||||
required: true,
|
||||
schema: {
|
||||
notTheTypeProperty: "string"
|
||||
}
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
result = validateParam( param, false, true )
|
||||
expect( result ).toEqual( [] )
|
||||
})
|
||||
|
||||
it("validates required strings", function() {
|
||||
// invalid string
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "string",
|
||||
value: ""
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// valid string
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "string",
|
||||
value: "test string"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid string with min and max length
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "string",
|
||||
value: "test string",
|
||||
maxLength: 50,
|
||||
minLength: 1
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates required strings with min and max length", function() {
|
||||
// invalid string with max length
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "string",
|
||||
value: "test string",
|
||||
maxLength: 5
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be less than MaxLength"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be less than MaxLength"])
|
||||
|
||||
// invalid string with max length 0
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "string",
|
||||
value: "test string",
|
||||
maxLength: 0
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be less than MaxLength"] )
|
||||
|
||||
}
|
||||
assertValidateParam(param, ["Value must be less than MaxLength"])
|
||||
|
||||
// invalid string with min length
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "string",
|
||||
value: "test string",
|
||||
minLength: 50
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be greater than MinLength"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be greater than MinLength"])
|
||||
})
|
||||
|
||||
it("validates optional strings", function() {
|
||||
// valid (empty) string
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "string",
|
||||
value: ""
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid string
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "string",
|
||||
value: "test"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates required files", function() {
|
||||
// invalid file
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "file",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// valid file
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "file",
|
||||
value: new win.File()
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates optional files", function() {
|
||||
// invalid file
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "file",
|
||||
value: "not a file"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be a file"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be a file"])
|
||||
|
||||
// valid (empty) file
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "file",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid file
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "file",
|
||||
value: new win.File()
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates required arrays", function() {
|
||||
// invalid (empty) array
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "array",
|
||||
value: []
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// invalid (not an array)
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "array",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// invalid array, items do not match correct type
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "array",
|
||||
value: [1],
|
||||
items: {
|
||||
type: "string"
|
||||
}
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [{index: 0, error: "Value must be a string"}] )
|
||||
}
|
||||
assertValidateParam(param, [{index: 0, error: "Value must be a string"}])
|
||||
|
||||
// valid array, with no 'type' for items
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "array",
|
||||
value: ["1"]
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid array, items match type
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "array",
|
||||
value: ["1"],
|
||||
items: {
|
||||
type: "string"
|
||||
}
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates optional arrays", function() {
|
||||
// valid, empty array
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "array",
|
||||
value: []
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// invalid, items do not match correct type
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "array",
|
||||
value: ["number"],
|
||||
items: {
|
||||
type: "number"
|
||||
}
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [{index: 0, error: "Value must be a number"}] )
|
||||
}
|
||||
assertValidateParam(param, [{index: 0, error: "Value must be a number"}])
|
||||
|
||||
// valid
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "array",
|
||||
value: ["test"],
|
||||
items: {
|
||||
type: "string"
|
||||
}
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates required booleans", function() {
|
||||
// invalid boolean value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "boolean",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// invalid boolean value (not a boolean)
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "boolean",
|
||||
value: "test string"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// valid boolean value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "boolean",
|
||||
value: "true"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid boolean value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "boolean",
|
||||
value: false
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates optional booleans", function() {
|
||||
// valid (empty) boolean value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "boolean",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// invalid boolean value (not a boolean)
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "boolean",
|
||||
value: "test string"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be a boolean"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be a boolean"])
|
||||
|
||||
// valid boolean value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "boolean",
|
||||
value: "true"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid boolean value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "boolean",
|
||||
value: false
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates required numbers", function() {
|
||||
// invalid number, string instead of a number
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "number",
|
||||
value: "test"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// invalid number, undefined value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "number",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// valid number with min and max
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "number",
|
||||
value: 10,
|
||||
minimum: 5,
|
||||
maximum: 99
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid negative number with min and max
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "number",
|
||||
value: -10,
|
||||
minimum: -50,
|
||||
maximum: -5
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// invalid number with maximum:0
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "number",
|
||||
value: 1,
|
||||
maximum: 0
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be less than Maximum"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be less than Maximum"])
|
||||
|
||||
// invalid number with minimum:0
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "number",
|
||||
value: -10,
|
||||
minimum: 0
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be greater than Minimum"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be greater than Minimum"])
|
||||
})
|
||||
|
||||
it("validates optional numbers", function() {
|
||||
// invalid number, string instead of a number
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "number",
|
||||
value: "test"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be a number"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be a number"])
|
||||
|
||||
// valid (empty) number
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "number",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// valid number
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "number",
|
||||
value: 10
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates required integers", function() {
|
||||
// invalid integer, string instead of an integer
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "integer",
|
||||
value: "test"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// invalid integer, undefined value
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "integer",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Required field is not provided"] )
|
||||
}
|
||||
assertValidateParam(param, ["Required field is not provided"])
|
||||
|
||||
// valid integer
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: true,
|
||||
type: "integer",
|
||||
value: 10
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
|
||||
it("validates optional integers", function() {
|
||||
// invalid integer, string instead of an integer
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "integer",
|
||||
value: "test"
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( ["Value must be an integer"] )
|
||||
}
|
||||
assertValidateParam(param, ["Value must be an integer"])
|
||||
|
||||
// valid (empty) integer
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "integer",
|
||||
value: undefined
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
|
||||
// integers
|
||||
param = fromJS({
|
||||
param = {
|
||||
required: false,
|
||||
type: "integer",
|
||||
value: 10
|
||||
})
|
||||
result = validateParam( param, false )
|
||||
expect( result ).toEqual( [] )
|
||||
}
|
||||
assertValidateParam(param, [])
|
||||
})
|
||||
})
|
||||
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect from "expect"
|
||||
import { render } from "enzyme"
|
||||
import { fromJS } from "immutable"
|
||||
import Info from "components/info"
|
||||
import Markdown from "components/providers/markdown"
|
||||
|
||||
describe("<Info/> Sanitization", function(){
|
||||
const dummyComponent = () => null
|
||||
const components = {
|
||||
Markdown
|
||||
}
|
||||
const props = {
|
||||
getComponent: c => components[c] || dummyComponent,
|
||||
info: fromJS({
|
||||
title: "Test Title **strong** <script>alert(1)</script>",
|
||||
description: "Description *with* <script>Markdown</script>"
|
||||
}),
|
||||
host: "example.test",
|
||||
basePath: "/api"
|
||||
}
|
||||
|
||||
it("renders sanitized .title content", function(){
|
||||
let wrapper = render(<Info {...props}/>)
|
||||
expect(wrapper.find(".title").html()).toEqual("Test Title **strong** <script>alert(1)</script>")
|
||||
})
|
||||
|
||||
it("renders sanitized .description content", function() {
|
||||
let wrapper = render(<Info {...props}/>)
|
||||
expect(wrapper.find(".description").html()).toEqual("<div class=\"markdown\"><p>Description <em>with</em> </p>\n</div>")
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,36 @@
|
||||
/* eslint-env mocha */
|
||||
import React from "react"
|
||||
import expect from "expect"
|
||||
import { render } from "enzyme"
|
||||
import Markdown from "components/providers/markdown"
|
||||
import { Markdown as OAS3Markdown } from "corePlugins/oas3/wrap-components/markdown.js"
|
||||
|
||||
describe("Markdown Script Sanitization", function() {
|
||||
describe("Swagger 2.0", function() {
|
||||
it("sanitizes <script> elements", function() {
|
||||
const str = `script <script>alert(1)</script>`
|
||||
const el = render(<Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="markdown"><p>script </p>\n</div>`)
|
||||
})
|
||||
|
||||
it("sanitizes <img> elements", function() {
|
||||
const str = `<img src=x onerror="alert('img-in-description')">`
|
||||
const el = render(<Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="markdown"><p><img src="x"></p>\n</div>`)
|
||||
})
|
||||
})
|
||||
|
||||
describe("OAS 3", function() {
|
||||
it("sanitizes <script> elements", function() {
|
||||
const str = `script <script>alert(1)</script>`
|
||||
const el = render(<OAS3Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="renderedMarkdown"><div><p>script </p></div></div>`)
|
||||
})
|
||||
|
||||
it("sanitizes <img> elements", function() {
|
||||
const str = `<img src=x onerror="alert('img-in-description')">`
|
||||
const el = render(<OAS3Markdown source={str} />)
|
||||
expect(el.html()).toEqual(`<div class="renderedMarkdown"><div><img src="x"></div></div>`)
|
||||
})
|
||||
})
|
||||
})
|
||||
Reference in New Issue
Block a user