feat: SRI security toggle

This commit is contained in:
NGPixel 2019-10-12 14:41:45 -04:00
parent 3de0e1499a
commit acb57879dd
10 changed files with 452 additions and 322 deletions

View File

@ -184,6 +184,16 @@
hint='Should be enabled when using a reverse-proxy like nginx, apache, CloudFlare, etc in front of Wiki.js. Turn off otherwise.' hint='Should be enabled when using a reverse-proxy like nginx, apache, CloudFlare, etc in front of Wiki.js. Turn off otherwise.'
) )
v-divider.mt-3
v-switch(
inset
label='Subresource Integrity'
color='red darken-2'
v-model='config.securitySRI'
persistent-hint
hint='This ensure that resources such as CSS and JS files are not altered during delivery.'
)
v-divider.mt-3 v-divider.mt-3
v-switch( v-switch(
inset inset
@ -262,6 +272,7 @@ export default {
securityIframe: true, securityIframe: true,
securityReferrerPolicy: true, securityReferrerPolicy: true,
securityTrustProxy: true, securityTrustProxy: true,
securitySRI: true,
securityHSTS: false, securityHSTS: false,
securityHSTSDuration: 0, securityHSTSDuration: 0,
securityCSP: false, securityCSP: false,
@ -309,6 +320,7 @@ export default {
securityIframe: _.get(this.config, 'securityIframe', false), securityIframe: _.get(this.config, 'securityIframe', false),
securityReferrerPolicy: _.get(this.config, 'securityReferrerPolicy', false), securityReferrerPolicy: _.get(this.config, 'securityReferrerPolicy', false),
securityTrustProxy: _.get(this.config, 'securityTrustProxy', false), securityTrustProxy: _.get(this.config, 'securityTrustProxy', false),
securitySRI: _.get(this.config, 'securitySRI', false),
securityHSTS: _.get(this.config, 'securityHSTS', false), securityHSTS: _.get(this.config, 'securityHSTS', false),
securityHSTSDuration: _.get(this.config, 'securityHSTSDuration', 0), securityHSTSDuration: _.get(this.config, 'securityHSTSDuration', 0),
securityCSP: _.get(this.config, 'securityCSP', false), securityCSP: _.get(this.config, 'securityCSP', false),

View File

@ -17,7 +17,7 @@
v-toolbar(color='grey darken-3', dark, dense, flat) v-toolbar(color='grey darken-3', dark, dense, flat)
.body-2 Virtual Folders .body-2 Virtual Folders
v-spacer v-spacer
v-btn(icon, tile) v-btn(icon, tile, href='https://docs.requarks.io/', target='_blank')
v-icon mdi-help-box v-icon mdi-help-box
v-treeview( v-treeview(
:active.sync='currentNode' :active.sync='currentNode'
@ -37,8 +37,8 @@
v-toolbar(color='blue darken-2', dark, dense, flat) v-toolbar(color='blue darken-2', dark, dense, flat)
.body-2 Pages .body-2 Pages
v-spacer v-spacer
v-btn(icon, tile): v-icon mdi-content-save-move-outline v-btn(icon, tile, disabled): v-icon mdi-content-save-move-outline
v-btn(icon, tile): v-icon mdi-trash-can-outline v-btn(icon, tile, disabled): v-icon mdi-trash-can-outline
v-list.py-0(dense, v-if='currentPages.length > 0') v-list.py-0(dense, v-if='currentPages.length > 0')
v-list-item-group( v-list-item-group(
v-model='currentPage' v-model='currentPage'
@ -131,6 +131,7 @@ export default {
children: [] children: []
}], }],
pages: [], pages: [],
all: [],
namespaces: siteLangs.length ? siteLangs.map(ns => ns.code) : [siteConfig.lang] namespaces: siteLangs.length ? siteLangs.map(ns => ns.code) : [siteConfig.lang]
} }
}, },
@ -162,6 +163,20 @@ export default {
this.$nextTick(() => { this.$nextTick(() => {
this.currentNode = oldValue this.currentNode = oldValue
}) })
} else {
if (this.openNodes.indexOf(newValue[0]) < 0) { // auto open and load children
const current = _.find(this.all, ['id', newValue[0]])
if (current) {
if (this.openNodes.indexOf(current.parent) < 0) {
this.$nextTick(() => {
this.openNodes.push(current.parent)
})
}
}
this.$nextTick(() => {
this.openNodes.push(newValue[0])
})
}
} }
}, },
currentPage (newValue, oldValue) { currentPage (newValue, oldValue) {
@ -204,6 +219,8 @@ export default {
} }
this.pages.push(...itemPages) this.pages.push(...itemPages)
this.all.push(...items)
this.searchLoading = false this.searchLoading = false
} }
} }

View File

@ -16,6 +16,7 @@
securityIframe securityIframe
securityReferrerPolicy securityReferrerPolicy
securityTrustProxy securityTrustProxy
securitySRI
securityHSTS securityHSTS
securityHSTSDuration securityHSTSDuration
securityCSP securityCSP

View File

@ -43,21 +43,11 @@ html
//- CSS //- CSS
<% for (var index in htmlWebpackPlugin.files.css) { %> <% for (var index in htmlWebpackPlugin.files.css) { %>
<% if (htmlWebpackPlugin.files.cssIntegrity) { %>
link(
type='text/css'
rel='stylesheet'
href='<%= htmlWebpackPlugin.files.css[index] %>'
integrity='<%= htmlWebpackPlugin.files.cssIntegrity[index] %>'
crossorigin='<%= webpackConfig.output.crossOriginLoading %>'
)
<% } else { %>
link( link(
type='text/css' type='text/css'
rel='stylesheet' rel='stylesheet'
href='<%= htmlWebpackPlugin.files.css[index] %>' href='<%= htmlWebpackPlugin.files.css[index] %>'
) )
<% } %>
<% } %> <% } %>
script( script(
@ -67,19 +57,10 @@ html
//- JS //- JS
<% for (var index in htmlWebpackPlugin.files.js) { %> <% for (var index in htmlWebpackPlugin.files.js) { %>
<% if (htmlWebpackPlugin.files.cssIntegrity) { %>
script(
type='text/javascript'
src='<%= htmlWebpackPlugin.files.js[index] %>'
integrity='<%= htmlWebpackPlugin.files.jsIntegrity[index] %>'
crossorigin='<%= webpackConfig.output.crossOriginLoading %>'
)
<% } else { %>
script( script(
type='text/javascript' type='text/javascript'
src='<%= htmlWebpackPlugin.files.js[index] %>' src='<%= htmlWebpackPlugin.files.js[index] %>'
) )
<% } %>
<% } %> <% } %>
!= analyticsCode.head != analyticsCode.head

View File

@ -52,7 +52,7 @@ html(lang=siteConfig.lang)
type='text/css' type='text/css'
rel='stylesheet' rel='stylesheet'
href='<%= htmlWebpackPlugin.files.css[index] %>' href='<%= htmlWebpackPlugin.files.css[index] %>'
integrity='<%= htmlWebpackPlugin.files.cssIntegrity[index] %>' integrity=config.security.securitySRI ? '<%= htmlWebpackPlugin.files.cssIntegrity[index] %>' : false
crossorigin='<%= webpackConfig.output.crossOriginLoading %>' crossorigin='<%= webpackConfig.output.crossOriginLoading %>'
) )
<% } else { %> <% } else { %>
@ -66,11 +66,11 @@ html(lang=siteConfig.lang)
//- JS //- JS
<% for (var index in htmlWebpackPlugin.files.js) { %> <% for (var index in htmlWebpackPlugin.files.js) { %>
<% if (htmlWebpackPlugin.files.cssIntegrity) { %> <% if (htmlWebpackPlugin.files.jsIntegrity) { %>
script( script(
type='text/javascript' type='text/javascript'
src='<%= htmlWebpackPlugin.files.js[index] %>' src='<%= htmlWebpackPlugin.files.js[index] %>'
integrity='<%= htmlWebpackPlugin.files.jsIntegrity[index] %>' integrity=config.security.securitySRI ? '<%= htmlWebpackPlugin.files.jsIntegrity[index] %>' : false
crossorigin='<%= webpackConfig.output.crossOriginLoading %>' crossorigin='<%= webpackConfig.output.crossOriginLoading %>'
) )
<% } else { %> <% } else { %>

View File

@ -35,22 +35,22 @@
}, },
"dependencies": { "dependencies": {
"@aoberoi/passport-slack": "1.0.5", "@aoberoi/passport-slack": "1.0.5",
"@bugsnag/js": "6.4.1", "@bugsnag/js": "6.4.2",
"@exlinc/keycloak-passport": "1.0.2", "@exlinc/keycloak-passport": "1.0.2",
"algoliasearch": "3.35.0", "algoliasearch": "3.35.1",
"apollo-fetch": "0.7.0", "apollo-fetch": "0.7.0",
"apollo-server": "2.9.4", "apollo-server": "2.9.6",
"apollo-server-express": "2.9.4", "apollo-server-express": "2.9.6",
"auto-load": "3.0.4", "auto-load": "3.0.4",
"aws-sdk": "2.538.0", "aws-sdk": "2.548.0",
"azure-search-client": "3.1.5", "azure-search-client": "3.1.5",
"bcryptjs-then": "1.0.1", "bcryptjs-then": "1.0.1",
"bluebird": "3.5.5", "bluebird": "3.7.0",
"body-parser": "1.19.0", "body-parser": "1.19.0",
"brute-knex": "4.0.0", "brute-knex": "4.0.0",
"chalk": "2.4.2", "chalk": "2.4.2",
"cheerio": "1.0.0-rc.3", "cheerio": "1.0.0-rc.3",
"chokidar": "3.1.1", "chokidar": "3.2.1",
"clean-css": "4.2.1", "clean-css": "4.2.1",
"compression": "1.7.4", "compression": "1.7.4",
"connect-session-knex": "1.4.0", "connect-session-knex": "1.4.0",
@ -59,35 +59,35 @@
"custom-error-instance": "2.1.1", "custom-error-instance": "2.1.1",
"dependency-graph": "0.8.0", "dependency-graph": "0.8.0",
"diff": "4.0.1", "diff": "4.0.1",
"diff2html": "2.11.3", "diff2html": "2.12.1",
"dotize": "0.3.0", "dotize": "0.3.0",
"elasticsearch6": "npm:@elastic/elasticsearch@6", "elasticsearch6": "npm:@elastic/elasticsearch@6",
"elasticsearch7": "npm:@elastic/elasticsearch@7", "elasticsearch7": "npm:@elastic/elasticsearch@7",
"emoji-regex": "8.0.0", "emoji-regex": "8.0.0",
"express": "4.17.1", "express": "4.17.1",
"express-brute": "1.0.1", "express-brute": "1.0.1",
"express-session": "1.16.2", "express-session": "1.17.0",
"file-type": "12.3.0", "file-type": "12.3.0",
"filesize": "4.2.1", "filesize": "5.0.3",
"fs-extra": "8.1.0", "fs-extra": "8.1.0",
"getos": "3.1.1", "getos": "3.1.1",
"graphql": "14.5.8", "graphql": "14.5.8",
"graphql-list-fields": "2.0.2", "graphql-list-fields": "2.0.2",
"graphql-rate-limit-directive": "1.1.0", "graphql-rate-limit-directive": "1.2.0",
"graphql-subscriptions": "1.1.0", "graphql-subscriptions": "1.1.0",
"graphql-tools": "4.0.5", "graphql-tools": "4.0.5",
"he": "1.2.0", "he": "1.2.0",
"highlight.js": "9.15.10", "highlight.js": "9.15.10",
"i18next": "17.0.16", "i18next": "17.2.0",
"i18next-express-middleware": "1.8.2", "i18next-express-middleware": "1.8.2",
"i18next-node-fs-backend": "2.1.3", "i18next-node-fs-backend": "2.1.3",
"image-size": "0.8.2", "image-size": "0.8.3",
"js-base64": "2.5.1", "js-base64": "2.5.1",
"js-binary": "1.2.0", "js-binary": "1.2.0",
"js-yaml": "3.13.1", "js-yaml": "3.13.1",
"jsonwebtoken": "8.5.1", "jsonwebtoken": "8.5.1",
"klaw": "3.0.0", "klaw": "3.0.0",
"knex": "0.19.4", "knex": "0.19.5",
"lodash": "4.17.15", "lodash": "4.17.15",
"markdown-it": "10.0.0", "markdown-it": "10.0.0",
"markdown-it-abbr": "1.0.4", "markdown-it-abbr": "1.0.4",
@ -111,10 +111,10 @@
"mssql": "5.1.0", "mssql": "5.1.0",
"multer": "1.4.2", "multer": "1.4.2",
"mysql2": "1.7.0", "mysql2": "1.7.0",
"nanoid": "2.1.1", "nanoid": "2.1.3",
"node-2fa": "1.1.2", "node-2fa": "1.1.2",
"node-cache": "4.2.1", "node-cache": "4.2.1",
"nodemailer": "6.3.0", "nodemailer": "6.3.1",
"objection": "1.6.11", "objection": "1.6.11",
"passport": "0.4.0", "passport": "0.4.0",
"passport-auth0": "1.2.1", "passport-auth0": "1.2.1",
@ -148,7 +148,7 @@
"request-promise": "4.2.4", "request-promise": "4.2.4",
"safe-regex": "2.0.2", "safe-regex": "2.0.2",
"sanitize-filename": "1.6.3", "sanitize-filename": "1.6.3",
"scim-query-filter-parser": "2.0.0", "scim-query-filter-parser": "2.0.1",
"semver": "6.3.0", "semver": "6.3.0",
"serve-favicon": "2.5.0", "serve-favicon": "2.5.0",
"simple-git": "1.126.0", "simple-git": "1.126.0",
@ -162,11 +162,11 @@
"uuid": "3.3.3", "uuid": "3.3.3",
"validate.js": "0.13.1", "validate.js": "0.13.1",
"winston": "3.2.1", "winston": "3.2.1",
"yargs": "14.0.0" "yargs": "14.2.0"
}, },
"devDependencies": { "devDependencies": {
"@babel/cli": "^7.6.2", "@babel/cli": "^7.6.4",
"@babel/core": "^7.6.2", "@babel/core": "^7.6.4",
"@babel/plugin-proposal-class-properties": "^7.5.0", "@babel/plugin-proposal-class-properties": "^7.5.0",
"@babel/plugin-proposal-decorators": "^7.6.0", "@babel/plugin-proposal-decorators": "^7.6.0",
"@babel/plugin-proposal-export-namespace-from": "^7.5.2", "@babel/plugin-proposal-export-namespace-from": "^7.5.2",
@ -177,11 +177,11 @@
"@babel/plugin-syntax-dynamic-import": "^7.2.0", "@babel/plugin-syntax-dynamic-import": "^7.2.0",
"@babel/plugin-syntax-import-meta": "^7.2.0", "@babel/plugin-syntax-import-meta": "^7.2.0",
"@babel/polyfill": "^7.6.0", "@babel/polyfill": "^7.6.0",
"@babel/preset-env": "^7.6.2", "@babel/preset-env": "^7.6.3",
"@mdi/font": "4.4.95", "@mdi/font": "4.5.95",
"@panter/vue-i18next": "0.15.1", "@panter/vue-i18next": "0.15.1",
"@requarks/ckeditor5": "12.4.0-wiki.14", "@requarks/ckeditor5": "12.4.0-wiki.14",
"@vue/babel-preset-app": "3.11.0", "@vue/babel-preset-app": "3.12.0",
"animate-sass": "0.8.2", "animate-sass": "0.8.2",
"animated-number-vue": "1.0.0", "animated-number-vue": "1.0.0",
"apollo-cache-inmemory": "1.6.3", "apollo-cache-inmemory": "1.6.3",
@ -193,7 +193,7 @@
"apollo-link-persisted-queries": "0.2.2", "apollo-link-persisted-queries": "0.2.2",
"apollo-link-ws": "1.0.19", "apollo-link-ws": "1.0.19",
"apollo-utilities": "1.3.2", "apollo-utilities": "1.3.2",
"autoprefixer": "9.6.1", "autoprefixer": "9.6.4",
"babel-eslint": "10.0.3", "babel-eslint": "10.0.3",
"babel-jest": "24.9.0", "babel-jest": "24.9.0",
"babel-loader": "^8.0.6", "babel-loader": "^8.0.6",
@ -211,7 +211,7 @@
"cssnano": "4.1.10", "cssnano": "4.1.10",
"duplicate-package-checker-webpack-plugin": "3.0.0", "duplicate-package-checker-webpack-plugin": "3.0.0",
"epic-spinners": "1.1.0", "epic-spinners": "1.1.0",
"eslint": "6.4.0", "eslint": "6.5.1",
"eslint-config-requarks": "1.0.7", "eslint-config-requarks": "1.0.7",
"eslint-config-standard": "14.1.0", "eslint-config-standard": "14.1.0",
"eslint-plugin-import": "2.18.2", "eslint-plugin-import": "2.18.2",
@ -223,7 +223,7 @@
"file-loader": "4.2.0", "file-loader": "4.2.0",
"filepond": "4.7.2", "filepond": "4.7.2",
"filepond-plugin-file-validate-type": "1.2.4", "filepond-plugin-file-validate-type": "1.2.4",
"filesize.js": "1.0.2", "filesize.js": "2.0.0",
"graphiql": "0.14.2", "graphiql": "0.14.2",
"graphql-persisted-document-loader": "1.0.1", "graphql-persisted-document-loader": "1.0.1",
"graphql-tag": "^2.10.1", "graphql-tag": "^2.10.1",
@ -253,19 +253,19 @@
"pug-plain-loader": "1.0.0", "pug-plain-loader": "1.0.0",
"raw-loader": "3.1.0", "raw-loader": "3.1.0",
"resolve-url-loader": "3.1.0", "resolve-url-loader": "3.1.0",
"sass": "1.22.12", "sass": "1.23.0",
"sass-loader": "8.0.0", "sass-loader": "8.0.0",
"sass-resources-loader": "2.0.1", "sass-resources-loader": "2.0.1",
"script-ext-html-webpack-plugin": "2.1.4", "script-ext-html-webpack-plugin": "2.1.4",
"simple-progress-webpack-plugin": "1.1.2", "simple-progress-webpack-plugin": "1.1.2",
"style-loader": "1.0.0", "style-loader": "1.0.0",
"terser": "4.3.3", "terser": "4.3.8",
"twemoji-awesome": "1.0.6", "twemoji-awesome": "1.0.6",
"url-loader": "2.1.0", "url-loader": "2.2.0",
"velocity-animate": "1.5.2", "velocity-animate": "1.5.2",
"viz.js": "2.1.2", "viz.js": "2.1.2",
"vue": "2.6.10", "vue": "2.6.10",
"vue-apollo": "3.0.0-rc.6", "vue-apollo": "3.0.0-rc.7",
"vue-chartjs": "3.4.2", "vue-chartjs": "3.4.2",
"vue-clipboards": "1.3.0", "vue-clipboards": "1.3.0",
"vue-filepond": "5.1.3", "vue-filepond": "5.1.3",
@ -278,22 +278,22 @@
"vue2-animate": "2.1.2", "vue2-animate": "2.1.2",
"vuedraggable": "2.23.2", "vuedraggable": "2.23.2",
"vuescroll": "4.14.4", "vuescroll": "4.14.4",
"vuetify": "2.0.19", "vuetify": "2.1.3",
"vuetify-loader": "1.3.0", "vuetify-loader": "1.3.0",
"vuex": "3.1.1", "vuex": "3.1.1",
"vuex-pathify": "1.4.0", "vuex-pathify": "1.4.0",
"vuex-persistedstate": "2.5.4", "vuex-persistedstate": "2.5.4",
"webpack": "4.41.0", "webpack": "4.41.1",
"webpack-bundle-analyzer": "3.5.2", "webpack-bundle-analyzer": "3.5.2",
"webpack-cli": "3.3.9", "webpack-cli": "3.3.9",
"webpack-dev-middleware": "3.7.1", "webpack-dev-middleware": "3.7.2",
"webpack-hot-middleware": "2.25.0", "webpack-hot-middleware": "2.25.0",
"webpack-merge": "4.2.2", "webpack-merge": "4.2.2",
"webpack-subresource-integrity": "1.3.3", "webpack-subresource-integrity": "1.3.4",
"webpackbar": "4.0.0", "webpackbar": "4.0.0",
"whatwg-fetch": "3.0.0", "whatwg-fetch": "3.0.0",
"write-file-webpack-plugin": "4.5.1", "write-file-webpack-plugin": "4.5.1",
"xterm": "4.0.2", "xterm": "4.1.0",
"zxcvbn": "4.4.2" "zxcvbn": "4.4.2"
}, },
"browserslist": [ "browserslist": [

View File

@ -46,6 +46,7 @@ defaults:
securityIframe: true securityIframe: true
securityReferrerPolicy: true securityReferrerPolicy: true
securityTrustProxy: true securityTrustProxy: true
securitySRI: true
securityHSTS: false securityHSTS: false
securityHSTSDuration: 300 securityHSTSDuration: 300
securityCSP: false securityCSP: false

View File

@ -47,6 +47,7 @@ module.exports = {
securityIframe: args.securityIframe, securityIframe: args.securityIframe,
securityReferrerPolicy: args.securityReferrerPolicy, securityReferrerPolicy: args.securityReferrerPolicy,
securityTrustProxy: args.securityTrustProxy, securityTrustProxy: args.securityTrustProxy,
securitySRI: args.securitySRI,
securityHSTS: args.securityHSTS, securityHSTS: args.securityHSTS,
securityHSTSDuration: args.securityHSTSDuration, securityHSTSDuration: args.securityHSTSDuration,
securityCSP: args.securityCSP, securityCSP: args.securityCSP,

View File

@ -39,6 +39,7 @@ type SiteMutation {
securityIframe: Boolean! securityIframe: Boolean!
securityReferrerPolicy: Boolean! securityReferrerPolicy: Boolean!
securityTrustProxy: Boolean! securityTrustProxy: Boolean!
securitySRI: Boolean!
securityHSTS: Boolean! securityHSTS: Boolean!
securityHSTSDuration: Int! securityHSTSDuration: Int!
securityCSP: Boolean! securityCSP: Boolean!
@ -66,6 +67,7 @@ type SiteConfig {
securityIframe: Boolean! securityIframe: Boolean!
securityReferrerPolicy: Boolean! securityReferrerPolicy: Boolean!
securityTrustProxy: Boolean! securityTrustProxy: Boolean!
securitySRI: Boolean!
securityHSTS: Boolean! securityHSTS: Boolean!
securityHSTSDuration: Int! securityHSTSDuration: Int!
securityCSP: Boolean! securityCSP: Boolean!

639
yarn.lock

File diff suppressed because it is too large Load Diff