mirror of
https://github.com/vuejs/vue-cli.git
synced 2026-03-09 17:09:05 -05:00
feat: vulnerability audit widget
This commit is contained in:
@@ -1,5 +1,5 @@
|
||||
<template>
|
||||
<div v-if="false" class="status-widget">
|
||||
<div v-if="implemented" class="status-widget">
|
||||
<div class="header">
|
||||
<div class="icon-wrapper">
|
||||
<ItemLogo
|
||||
@@ -14,9 +14,10 @@
|
||||
<div class="last-updated">
|
||||
<template v-if="status.lastUpdate">
|
||||
<div class="label">
|
||||
{{ $t('org.vue.widgets.status-widget.last-updated') }}
|
||||
{{ message || $t('org.vue.widgets.status-widget.last-updated') }}
|
||||
</div>
|
||||
<VueTimeago
|
||||
v-if="!message"
|
||||
:datetime="status.lastUpdate"
|
||||
:auto-update="60"
|
||||
/>
|
||||
@@ -73,6 +74,17 @@ export default {
|
||||
status: {
|
||||
type: Object,
|
||||
required: true
|
||||
},
|
||||
|
||||
message: {
|
||||
type: String,
|
||||
default: null
|
||||
},
|
||||
|
||||
// TODO remove
|
||||
implemented: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
@@ -2,12 +2,23 @@
|
||||
<div class="vulnerability">
|
||||
<StatusWidget
|
||||
v-if="status"
|
||||
:icon="icons[status.status]"
|
||||
:icon-class="iconClasses[status.status]"
|
||||
:icon="status.status === 'attention' ? severity.icon : icons[status.status]"
|
||||
:icon-class="status.status === 'attention' ? severity.class : iconClasses[status.status]"
|
||||
:title="$t(`org.vue.widgets.vulnerability.messages.${status.status}`, { n: status.count })"
|
||||
:status="status"
|
||||
:message="status.message"
|
||||
implemented
|
||||
@check="checkForUpdates()"
|
||||
/>
|
||||
>
|
||||
<template #more-actions>
|
||||
<VueButton
|
||||
v-if="status.status !== 'loading'"
|
||||
:label="$t('org.vue.widgets.vulnerability.recheck')"
|
||||
icon-left="refresh"
|
||||
@click="refresh()"
|
||||
/>
|
||||
</template>
|
||||
</StatusWidget>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -18,8 +29,28 @@ import StatusWidget from './StatusWidget.vue'
|
||||
|
||||
const UPDATES_ICONS = {
|
||||
'ok': 'verified_user',
|
||||
'loading': 'hourglass_full',
|
||||
'attention': 'error'
|
||||
'loading': 'hourglass_empty',
|
||||
'attention': 'error',
|
||||
'error': 'error'
|
||||
}
|
||||
|
||||
export const SEVERITIES = {
|
||||
critical: {
|
||||
class: 'danger',
|
||||
icon: 'new_releases'
|
||||
},
|
||||
high: {
|
||||
class: 'danger',
|
||||
icon: 'error'
|
||||
},
|
||||
moderate: {
|
||||
class: 'warning',
|
||||
icon: 'error'
|
||||
},
|
||||
low: {
|
||||
class: '',
|
||||
icon: 'error'
|
||||
}
|
||||
}
|
||||
|
||||
export default {
|
||||
@@ -33,14 +64,20 @@ export default {
|
||||
})
|
||||
},
|
||||
|
||||
computed: {
|
||||
severity () {
|
||||
return this.status && SEVERITIES[this.status.severity]
|
||||
}
|
||||
},
|
||||
|
||||
created () {
|
||||
this.icons = UPDATES_ICONS
|
||||
this.iconClasses = UPDATES_ICON_CLASSES
|
||||
},
|
||||
|
||||
methods: {
|
||||
checkForUpdates () {
|
||||
// TODO
|
||||
refresh () {
|
||||
this.$callPluginAction('org.vue.widgets.actions.check-vunerability')
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -12,15 +12,48 @@
|
||||
<div class="title">
|
||||
{{ $t('org.vue.widgets.vulnerability.messages.attention', { n: details.vulnerabilities.length }) }}
|
||||
</div>
|
||||
|
||||
<div class="summary">
|
||||
<div
|
||||
v-for="(severity, key) of severities"
|
||||
:key="key"
|
||||
:class="`severity-${severity.class}`"
|
||||
class="summary-item"
|
||||
>
|
||||
<VueIcon
|
||||
:icon="severity.icon"
|
||||
:class="severity.class"
|
||||
/>
|
||||
<span class="count">{{ details.summary[key] }}</span>
|
||||
{{ $t(`org.vue.widgets.vulnerability.severity.${key}`) }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="items">
|
||||
<VulnerabilityItem
|
||||
v-for="(item, index) of details.vulnerabilities"
|
||||
:key="index"
|
||||
:item="item"
|
||||
/>
|
||||
</div>
|
||||
<transition name="vue-ui-fade">
|
||||
<DynamicScroller
|
||||
v-if="showList"
|
||||
ref="scroller"
|
||||
class="items"
|
||||
:items="details.vulnerabilities"
|
||||
:min-item-size="75"
|
||||
v-slot="{ item, active }"
|
||||
>
|
||||
<DynamicScrollerItem
|
||||
:item="item"
|
||||
:active="active"
|
||||
:size-dependencies="[
|
||||
showMoreParentsMap[item.id]
|
||||
]"
|
||||
>
|
||||
<VulnerabilityItem
|
||||
:item="item"
|
||||
:show-more-parents="showMoreParentsMap[item.id]"
|
||||
@toggle-more-parents="$set(showMoreParentsMap, item.id, !showMoreParentsMap[item.id])"
|
||||
/>
|
||||
</DynamicScrollerItem>
|
||||
</DynamicScroller>
|
||||
</transition>
|
||||
</template>
|
||||
</div>
|
||||
</template>
|
||||
@@ -28,6 +61,8 @@
|
||||
<script>
|
||||
import VulnerabilityItem from './VulnerabilityItem.vue'
|
||||
|
||||
import { SEVERITIES } from './Vulnerability.vue'
|
||||
|
||||
export default {
|
||||
components: {
|
||||
VulnerabilityItem
|
||||
@@ -37,6 +72,24 @@ export default {
|
||||
return mapSharedData('org.vue.widgets.vulnerability.', {
|
||||
details: 'details'
|
||||
})
|
||||
},
|
||||
|
||||
data () {
|
||||
return {
|
||||
showList: false,
|
||||
showMoreParentsMap: {}
|
||||
}
|
||||
},
|
||||
|
||||
created () {
|
||||
this.severities = SEVERITIES
|
||||
},
|
||||
|
||||
mounted () {
|
||||
// Animation breaks scroller item sizes
|
||||
setTimeout(() => {
|
||||
this.showList = true
|
||||
}, 200)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -45,9 +98,32 @@ export default {
|
||||
@import "~@vue/cli-ui/src/style/imports"
|
||||
|
||||
.vulnerability-details
|
||||
overflow-x hidden
|
||||
overflow-y auto
|
||||
v-box()
|
||||
|
||||
.pane-toolbar
|
||||
padding-bottom $padding-item
|
||||
|
||||
.summary
|
||||
display flex
|
||||
padding-right 12px
|
||||
|
||||
.summary-item
|
||||
display flex
|
||||
align-items center
|
||||
margin-left 16px
|
||||
|
||||
.vue-ui-icon,
|
||||
.count
|
||||
margin-right 3px
|
||||
|
||||
.count
|
||||
font-weight bold
|
||||
|
||||
.severity-danger
|
||||
color $vue-ui-color-danger
|
||||
.severity-warning
|
||||
color $vue-ui-color-warning
|
||||
|
||||
.items
|
||||
flex 1
|
||||
</style>
|
||||
|
||||
@@ -2,84 +2,114 @@
|
||||
<div class="vulnerability-item list-item">
|
||||
<div class="wrapper">
|
||||
<ItemLogo
|
||||
image="error"
|
||||
:image="severity.icon"
|
||||
:class="severity.class"
|
||||
/>
|
||||
|
||||
<ListItemInfo
|
||||
:link="item.moreInfo"
|
||||
>
|
||||
<template slot="name">
|
||||
<span class="name">{{ item.name }}</span>
|
||||
<span class="version">{{ item.version }}</span>
|
||||
</template>
|
||||
|
||||
<template slot="description">
|
||||
<span
|
||||
class="severity"
|
||||
:class="severity.class"
|
||||
>
|
||||
{{ $t(`org.vue.widgets.vulnerability.severity.${item.severity}`) }}
|
||||
</span>
|
||||
|
||||
<span class="message">
|
||||
{{ item.message }}
|
||||
</span>
|
||||
</template>
|
||||
</ListItemInfo>
|
||||
|
||||
<div class="parents">
|
||||
<div v-if="!item.parents" class="vue-ui-empty">
|
||||
{{ $t('org.vue.widgets.vulnerability.direct-dep') }}
|
||||
</div>
|
||||
|
||||
<template v-else>
|
||||
<div
|
||||
v-for="(parent, index) of item.parents"
|
||||
:key="index"
|
||||
class="parent"
|
||||
>
|
||||
<span class="name">{{ parent.name }}</span>
|
||||
<span class="version">{{ parent.version }}</span>
|
||||
<VueIcon
|
||||
icon="chevron_right"
|
||||
class="separator-icon medium"
|
||||
/>
|
||||
</div>
|
||||
<div class="parent current">
|
||||
<div class="main-infos">
|
||||
<ListItemInfo
|
||||
:link="item.moreInfo"
|
||||
>
|
||||
<template slot="name">
|
||||
<span class="name">{{ item.name }}</span>
|
||||
<span class="version">{{ item.version }}</span>
|
||||
</template>
|
||||
|
||||
<template slot="description">
|
||||
<span
|
||||
class="severity"
|
||||
:class="severity.class"
|
||||
>
|
||||
{{ $t(`org.vue.widgets.vulnerability.severity.${item.severity}`) }}
|
||||
</span>
|
||||
<span class="title" v-tooltip="item.message">
|
||||
{{ item.title }}
|
||||
</span>
|
||||
</template>
|
||||
</ListItemInfo>
|
||||
|
||||
<div class="info-versions">
|
||||
<div class="info-version">
|
||||
<VueIcon icon="error"/>
|
||||
{{ $t('org.vue.widgets.vulnerability.versions.vulnerable') }}
|
||||
<span class="version">{{ item.versions.vulnerable }}</span>
|
||||
</div>
|
||||
</template>
|
||||
<div class="info-version">
|
||||
<VueIcon icon="check_circle"/>
|
||||
{{ $t('org.vue.widgets.vulnerability.versions.patched') }}
|
||||
<span class="version">{{ item.versions.patched }}</span>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="recommendation vue-ui-text success banner">
|
||||
<VueIcon icon="arrow_forward" class="big"/>
|
||||
{{ item.recommendation }}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="parents-list">
|
||||
<div
|
||||
v-for="(parents, index) of displayedParents"
|
||||
:key="index"
|
||||
class="parents"
|
||||
>
|
||||
<div v-if="!parents.length" class="vue-ui-empty">
|
||||
{{ $t('org.vue.widgets.vulnerability.direct-dep') }}
|
||||
</div>
|
||||
|
||||
<template v-else>
|
||||
<div
|
||||
v-for="(parent, index) of parents"
|
||||
:key="index"
|
||||
class="parent"
|
||||
>
|
||||
<span class="name">{{ parent.name }}</span>
|
||||
<VueIcon
|
||||
icon="chevron_right"
|
||||
class="separator-icon medium"
|
||||
/>
|
||||
</div>
|
||||
<div class="parent current">
|
||||
<span class="name">{{ item.name }}</span>
|
||||
</div>
|
||||
</template>
|
||||
</div>
|
||||
|
||||
<div v-if="item.parents.length > 3" class="show-more">
|
||||
<VueButton
|
||||
:icon-left="showMoreParents ? 'expand_less' : 'expand_more'"
|
||||
class="flat"
|
||||
@click="$emit('toggle-more-parents')"
|
||||
>
|
||||
{{ $t(`org.vue.common.show-${showMoreParents ? 'less' : 'more'}`) }}
|
||||
</VueButton>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
const SEVERITIES = {
|
||||
high: {
|
||||
class: 'danger'
|
||||
},
|
||||
medium: {
|
||||
class: 'warning'
|
||||
},
|
||||
low: {
|
||||
class: ''
|
||||
}
|
||||
}
|
||||
import { SEVERITIES } from './Vulnerability.vue'
|
||||
|
||||
export default {
|
||||
props: {
|
||||
item: {
|
||||
type: Object,
|
||||
required: true
|
||||
},
|
||||
showMoreParents: {
|
||||
type: Boolean
|
||||
}
|
||||
},
|
||||
|
||||
computed: {
|
||||
severity () {
|
||||
return SEVERITIES[this.item.severity]
|
||||
},
|
||||
|
||||
displayedParents () {
|
||||
return this.showMoreParents ? this.item.parents : this.item.parents.slice(0, 3)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -94,13 +124,16 @@ export default {
|
||||
|
||||
.wrapper
|
||||
h-box()
|
||||
box-center()
|
||||
|
||||
.list-item-info
|
||||
.main-infos
|
||||
flex 1
|
||||
|
||||
.name
|
||||
font-weight bold
|
||||
.name
|
||||
font-weight bold
|
||||
|
||||
.title
|
||||
cursor help
|
||||
border-bottom 1px dotted
|
||||
|
||||
.version
|
||||
margin-left 4px
|
||||
@@ -108,14 +141,27 @@ export default {
|
||||
font-size .9em
|
||||
|
||||
.severity
|
||||
color $color-text-light
|
||||
color $vue-ui-color-dark
|
||||
.vue-ui-dark-mode &
|
||||
color $vue-ui-color-light
|
||||
&.danger
|
||||
color $vue-ui-color-danger
|
||||
&.warning
|
||||
color $vue-ui-color-warning
|
||||
|
||||
.parents-list
|
||||
margin-left 12px
|
||||
width 50%
|
||||
|
||||
.parents
|
||||
h-box()
|
||||
margin 12px 0
|
||||
flex-wrap wrap
|
||||
width 100%
|
||||
|
||||
.parent
|
||||
&:not(:first-child)
|
||||
opacity .7
|
||||
|
||||
.separator-icon
|
||||
>>> svg
|
||||
@@ -123,4 +169,24 @@ export default {
|
||||
|
||||
.vue-ui-empty
|
||||
padding 0
|
||||
|
||||
.info-versions
|
||||
margin-top 4px
|
||||
|
||||
.info-version
|
||||
display flex
|
||||
align-items baseline
|
||||
margin-top 2px
|
||||
|
||||
.vue-ui-icon
|
||||
margin-right 4px
|
||||
opacity .5
|
||||
|
||||
.version
|
||||
margin-left 8px
|
||||
|
||||
.recommendation
|
||||
margin 8px 0
|
||||
display inline-flex
|
||||
align-items center
|
||||
</style>
|
||||
|
||||
@@ -4,7 +4,9 @@
|
||||
"common": {
|
||||
"close": "Close",
|
||||
"back": "Go back",
|
||||
"more-info": "More info"
|
||||
"more-info": "More info",
|
||||
"show-more": "Show more",
|
||||
"show-less": "Show less"
|
||||
},
|
||||
"components": {
|
||||
"client-addon-component": {
|
||||
@@ -811,15 +813,22 @@
|
||||
"description": "Check for known vulnerabilities in your project dependencies",
|
||||
"messages": {
|
||||
"ok": "No vulnerability found",
|
||||
"loading": "Checking security reports...",
|
||||
"attention": "{n} vulnerabilities found"
|
||||
"loading": "Auditing project security...",
|
||||
"attention": "{n} vulnerabilities found",
|
||||
"error": "Couldn't check for vulnerability"
|
||||
},
|
||||
"severity": {
|
||||
"critical": "Critical severity",
|
||||
"high": "High severity",
|
||||
"medium": "Medium severity",
|
||||
"moderate": "Medium severity",
|
||||
"low": "Low severity"
|
||||
},
|
||||
"direct-dep": "Direct dependency"
|
||||
"direct-dep": "Direct dependency",
|
||||
"versions": {
|
||||
"vulnerable": "Vulnerable versions:",
|
||||
"patched": "Patched versions:"
|
||||
},
|
||||
"recheck": "Check again"
|
||||
},
|
||||
"run-task": {
|
||||
"title": "Run task",
|
||||
|
||||
@@ -59,6 +59,7 @@
|
||||
"semver": "^5.5.0",
|
||||
"shortid": "^2.2.11",
|
||||
"vue-cli-plugin-apollo": "^0.19.1",
|
||||
"vue-virtual-scroller": "^1.0.0-rc.2",
|
||||
"watch": "^1.0.2"
|
||||
},
|
||||
"devDependencies": {
|
||||
|
||||
@@ -13,6 +13,8 @@ import SetSize from './util/set-size'
|
||||
import Focus from './util/focus'
|
||||
import Bus from './util/bus'
|
||||
import AnsiColors from './util/ansi-colors'
|
||||
import VueVirtualScroller from 'vue-virtual-scroller'
|
||||
import 'vue-virtual-scroller/dist/vue-virtual-scroller.css'
|
||||
|
||||
Vue.use(InstantSearch)
|
||||
Vue.use(VueMeta)
|
||||
@@ -48,3 +50,5 @@ Vue.mixin(ClientState)
|
||||
|
||||
Vue.directive('set-size', SetSize)
|
||||
Vue.directive('focus', Focus)
|
||||
|
||||
Vue.use(VueVirtualScroller)
|
||||
|
||||
121
packages/@vue/cli-ui/ui-defaults/utils/audit.js
Normal file
121
packages/@vue/cli-ui/ui-defaults/utils/audit.js
Normal file
@@ -0,0 +1,121 @@
|
||||
const { hasProjectYarn, execa } = require('@vue/cli-shared-utils')
|
||||
|
||||
const severity = {
|
||||
critical: 0,
|
||||
high: 1,
|
||||
moderate: 2,
|
||||
low: 3
|
||||
}
|
||||
|
||||
exports.auditProject = async function (cwd) {
|
||||
try {
|
||||
if (hasProjectYarn) {
|
||||
const child = await execa('yarn', [
|
||||
'audit',
|
||||
'--json',
|
||||
'--non-interactive',
|
||||
'--no-progress'
|
||||
], {
|
||||
cwd,
|
||||
reject: false
|
||||
})
|
||||
|
||||
const data = child.stdout
|
||||
|
||||
let auditAdvisories = []
|
||||
|
||||
const ids = {}
|
||||
|
||||
const lines = data.split(`\n`).filter(l => l.trim()).map(l => JSON.parse(l))
|
||||
for (const line of lines) {
|
||||
if (line.type === 'auditAdvisory') {
|
||||
if (!ids[line.data.advisory.id]) {
|
||||
auditAdvisories.push(line)
|
||||
ids[line.data.advisory.id] = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
const details = {
|
||||
vulnerabilities: [],
|
||||
summary: {
|
||||
critical: 0,
|
||||
high: 0,
|
||||
moderate: 0,
|
||||
low: 0
|
||||
}
|
||||
}
|
||||
|
||||
auditAdvisories = auditAdvisories.sort((a, b) => severity[a.data.advisory.severity] - severity[b.data.advisory.severity])
|
||||
|
||||
let id = 0
|
||||
for (const { data: { advisory } } of auditAdvisories) {
|
||||
for (const finding of advisory.findings) {
|
||||
// const [finding] = advisory.findings
|
||||
const detail = {
|
||||
id: id++,
|
||||
name: advisory.module_name,
|
||||
version: finding.version,
|
||||
parents: finding.paths.sort(
|
||||
(a, b) => a.length - b.length
|
||||
).map(
|
||||
parents => parents.split('>').slice(0, parents.length - 2).map(p => ({
|
||||
name: p
|
||||
}))
|
||||
),
|
||||
moreInfo: advisory.url,
|
||||
severity: advisory.severity,
|
||||
title: advisory.title,
|
||||
message: advisory.overview,
|
||||
versions: {
|
||||
vulnerable: advisory.vulnerable_versions,
|
||||
patched: advisory.patched_versions
|
||||
},
|
||||
recommendation: advisory.recommendation
|
||||
}
|
||||
details.vulnerabilities.push(detail)
|
||||
details.summary[advisory.severity]++
|
||||
}
|
||||
}
|
||||
|
||||
const status = {
|
||||
status: 'ok',
|
||||
count: details.vulnerabilities.length,
|
||||
message: null
|
||||
}
|
||||
|
||||
if (status.count) {
|
||||
status.status = 'attention'
|
||||
}
|
||||
|
||||
for (const n in details.summary) {
|
||||
if (details.summary) {
|
||||
status.severity = n
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
status,
|
||||
details
|
||||
}
|
||||
} else {
|
||||
// TODO NPM audit
|
||||
return {
|
||||
status: {
|
||||
status: 'error',
|
||||
message: 'Not implemented for NPM projects yet'
|
||||
},
|
||||
details: null
|
||||
}
|
||||
}
|
||||
} catch (e) {
|
||||
return {
|
||||
status: {
|
||||
status: 'error',
|
||||
message: e.message
|
||||
},
|
||||
details: null
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -96,51 +96,16 @@ module.exports = api => {
|
||||
|
||||
// Vulnerability check
|
||||
|
||||
let lastAudit = null
|
||||
setSharedData('vulnerability.status', {
|
||||
status: 'attention',
|
||||
lastUpdate: Date.now(),
|
||||
count: 3
|
||||
status: 'loading',
|
||||
lastUpdate: lastAudit,
|
||||
count: 0,
|
||||
message: null
|
||||
})
|
||||
setSharedData('vulnerability.details', {
|
||||
vulnerabilities: [
|
||||
{
|
||||
name: 'bquery',
|
||||
version: '0.1.2',
|
||||
parents: [
|
||||
{
|
||||
name: 'draphql',
|
||||
version: '1.8.7'
|
||||
}
|
||||
],
|
||||
moreInfo: 'https://vuejs.org/',
|
||||
severity: 'high',
|
||||
message: 'Regular Expression Denial of Service'
|
||||
},
|
||||
{
|
||||
name: 'leff-pad',
|
||||
version: '5.3.9-alpha.1',
|
||||
parents: [
|
||||
{
|
||||
name: 'view-ssr',
|
||||
version: '3.0.0-alpha.12'
|
||||
},
|
||||
{
|
||||
name: 'elpress',
|
||||
version: '1.17.3'
|
||||
}
|
||||
],
|
||||
moreInfo: 'https://vuejs.org/',
|
||||
severity: 'medium',
|
||||
message: 'Prototype Pollution'
|
||||
},
|
||||
{
|
||||
name: 'yterm',
|
||||
version: '4.6.2',
|
||||
moreInfo: 'https://vuejs.org/',
|
||||
severity: 'low',
|
||||
message: 'Regular Expression Denial of Service'
|
||||
}
|
||||
]
|
||||
vulnerabilities: [],
|
||||
summary: {}
|
||||
})
|
||||
registerWidget({
|
||||
id: 'vulnerability',
|
||||
@@ -155,6 +120,24 @@ module.exports = api => {
|
||||
maxHeight: 1,
|
||||
maxCount: 1
|
||||
})
|
||||
async function checkVulnerability (params) {
|
||||
setSharedData('vulnerability.status', {
|
||||
status: 'loading',
|
||||
lastUpdate: lastAudit,
|
||||
count: 0,
|
||||
message: null
|
||||
})
|
||||
|
||||
const { auditProject } = require('./utils/audit')
|
||||
const { status, details } = await auditProject(api.getCwd())
|
||||
|
||||
status.lastUpdate = lastAudit = Date.now()
|
||||
|
||||
setSharedData('vulnerability.status', status)
|
||||
setSharedData('vulnerability.details', details)
|
||||
}
|
||||
onAction('actions.check-vunerability', checkVulnerability)
|
||||
checkVulnerability()
|
||||
|
||||
// Run task
|
||||
|
||||
|
||||
100
yarn.lock
100
yarn.lock
@@ -3110,11 +3110,36 @@ babel-code-frame@^6.22.0, babel-code-frame@^6.26.0:
|
||||
esutils "^2.0.2"
|
||||
js-tokens "^3.0.2"
|
||||
|
||||
babel-core@7.0.0-bridge.0, babel-core@^6.0.0:
|
||||
babel-core@7.0.0-bridge.0:
|
||||
version "7.0.0-bridge.0"
|
||||
resolved "https://registry.yarnpkg.com/babel-core/-/babel-core-7.0.0-bridge.0.tgz#95a492ddd90f9b4e9a4a1da14eb335b87b634ece"
|
||||
integrity sha512-poPX9mZH/5CSanm50Q+1toVci6pv5KSRv/5TWCwtzQS5XEwn40BcCrgIeMFWP9CKKIniKXNxoIOnOq4VVlGXhg==
|
||||
|
||||
babel-core@^6.0.0, babel-core@^6.26.0:
|
||||
version "6.26.3"
|
||||
resolved "https://registry.yarnpkg.com/babel-core/-/babel-core-6.26.3.tgz#b2e2f09e342d0f0c88e2f02e067794125e75c207"
|
||||
integrity sha512-6jyFLuDmeidKmUEb3NM+/yawG0M2bDZ9Z1qbZP59cyHLz8kYGKYwpJP0UwUKKUiTRNvxfLesJnTedqczP7cTDA==
|
||||
dependencies:
|
||||
babel-code-frame "^6.26.0"
|
||||
babel-generator "^6.26.0"
|
||||
babel-helpers "^6.24.1"
|
||||
babel-messages "^6.23.0"
|
||||
babel-register "^6.26.0"
|
||||
babel-runtime "^6.26.0"
|
||||
babel-template "^6.26.0"
|
||||
babel-traverse "^6.26.0"
|
||||
babel-types "^6.26.0"
|
||||
babylon "^6.18.0"
|
||||
convert-source-map "^1.5.1"
|
||||
debug "^2.6.9"
|
||||
json5 "^0.5.1"
|
||||
lodash "^4.17.4"
|
||||
minimatch "^3.0.4"
|
||||
path-is-absolute "^1.0.1"
|
||||
private "^0.1.8"
|
||||
slash "^1.0.0"
|
||||
source-map "^0.5.7"
|
||||
|
||||
babel-eslint@^10.0.1:
|
||||
version "10.0.1"
|
||||
resolved "https://registry.yarnpkg.com/babel-eslint/-/babel-eslint-10.0.1.tgz#919681dc099614cd7d31d45c8908695092a1faed"
|
||||
@@ -3146,7 +3171,7 @@ babel-extract-comments@^1.0.0:
|
||||
dependencies:
|
||||
babylon "^6.18.0"
|
||||
|
||||
babel-generator@^6.18.0:
|
||||
babel-generator@^6.18.0, babel-generator@^6.26.0:
|
||||
version "6.26.1"
|
||||
resolved "https://registry.yarnpkg.com/babel-generator/-/babel-generator-6.26.1.tgz#1844408d3b8f0d35a404ea7ac180f087a601bd90"
|
||||
integrity sha512-HyfwY6ApZj7BYTcJURpM5tznulaBvyio7/0d4zFOeMPUmfxkCjHocCuoLa2SAGzBI8AREcH3eP3758F672DppA==
|
||||
@@ -3160,6 +3185,14 @@ babel-generator@^6.18.0:
|
||||
source-map "^0.5.7"
|
||||
trim-right "^1.0.1"
|
||||
|
||||
babel-helpers@^6.24.1:
|
||||
version "6.24.1"
|
||||
resolved "https://registry.yarnpkg.com/babel-helpers/-/babel-helpers-6.24.1.tgz#3471de9caec388e5c850e597e58a26ddf37602b2"
|
||||
integrity sha1-NHHenK7DiOXIUOWX5Yom3fN2ArI=
|
||||
dependencies:
|
||||
babel-runtime "^6.22.0"
|
||||
babel-template "^6.24.1"
|
||||
|
||||
babel-jest@^23.6.0:
|
||||
version "23.6.0"
|
||||
resolved "https://registry.yarnpkg.com/babel-jest/-/babel-jest-23.6.0.tgz#a644232366557a2240a0c083da6b25786185a2f1"
|
||||
@@ -3246,6 +3279,19 @@ babel-preset-jest@^23.2.0:
|
||||
babel-plugin-jest-hoist "^23.2.0"
|
||||
babel-plugin-syntax-object-rest-spread "^6.13.0"
|
||||
|
||||
babel-register@^6.26.0:
|
||||
version "6.26.0"
|
||||
resolved "https://registry.yarnpkg.com/babel-register/-/babel-register-6.26.0.tgz#6ed021173e2fcb486d7acb45c6009a856f647071"
|
||||
integrity sha1-btAhFz4vy0htestFxgCahW9kcHE=
|
||||
dependencies:
|
||||
babel-core "^6.26.0"
|
||||
babel-runtime "^6.26.0"
|
||||
core-js "^2.5.0"
|
||||
home-or-tmp "^2.0.0"
|
||||
lodash "^4.17.4"
|
||||
mkdirp "^0.5.1"
|
||||
source-map-support "^0.4.15"
|
||||
|
||||
babel-runtime@^6.18.0, babel-runtime@^6.22.0, babel-runtime@^6.26.0:
|
||||
version "6.26.0"
|
||||
resolved "https://registry.yarnpkg.com/babel-runtime/-/babel-runtime-6.26.0.tgz#965c7058668e82b55d7bfe04ff2337bc8b5647fe"
|
||||
@@ -3254,7 +3300,7 @@ babel-runtime@^6.18.0, babel-runtime@^6.22.0, babel-runtime@^6.26.0:
|
||||
core-js "^2.4.0"
|
||||
regenerator-runtime "^0.11.0"
|
||||
|
||||
babel-template@^6.16.0, babel-template@^6.26.0:
|
||||
babel-template@^6.16.0, babel-template@^6.24.1, babel-template@^6.26.0:
|
||||
version "6.26.0"
|
||||
resolved "https://registry.yarnpkg.com/babel-template/-/babel-template-6.26.0.tgz#de03e2d16396b069f46dd9fff8521fb1a0e35e02"
|
||||
integrity sha1-3gPi0WOWsGn0bdn/+FIfsaDjXgI=
|
||||
@@ -4770,7 +4816,7 @@ conventional-recommended-bump@^4.0.4:
|
||||
meow "^4.0.0"
|
||||
q "^1.5.1"
|
||||
|
||||
convert-source-map@^1.1.0, convert-source-map@^1.4.0:
|
||||
convert-source-map@^1.1.0, convert-source-map@^1.4.0, convert-source-map@^1.5.1:
|
||||
version "1.6.0"
|
||||
resolved "https://registry.yarnpkg.com/convert-source-map/-/convert-source-map-1.6.0.tgz#51b537a8c43e0f04dec1993bffcdd504e758ac20"
|
||||
integrity sha512-eFu7XigvxdZ1ETfbgPBohgyQ/Z++C0eEhTor0qRwBw9unw+L0/6V8wkSuGgzdThkiS5lSpdptOQPD8Ak40a+7A==
|
||||
@@ -4823,7 +4869,7 @@ core-js@^2.4.0, core-js@^2.5.7:
|
||||
resolved "https://registry.yarnpkg.com/core-js/-/core-js-2.6.3.tgz#4b70938bdffdaf64931e66e2db158f0892289c49"
|
||||
integrity sha512-l00tmFFZOBHtYhN4Cz7k32VM7vTn3rE2ANjQDxdEN6zmXZ/xq1jQuutnmHvMG1ZJ7xd72+TA5YpUK8wz3rWsfQ==
|
||||
|
||||
core-js@^2.6.5:
|
||||
core-js@^2.5.0, core-js@^2.6.5:
|
||||
version "2.6.5"
|
||||
resolved "https://registry.yarnpkg.com/core-js/-/core-js-2.6.5.tgz#44bc8d249e7fb2ff5d00e0341a7ffb94fbf67895"
|
||||
integrity sha512-klh/kDpwX8hryYL14M9w/xei6vrv6sE8gTHDG7/T/+SEovB/G4ejwcfE/CBzO6Edsu+OETZMZ3wcX/EjUkrl5A==
|
||||
@@ -8295,6 +8341,14 @@ hogan.js@^3.0.2:
|
||||
mkdirp "0.3.0"
|
||||
nopt "1.0.10"
|
||||
|
||||
home-or-tmp@^2.0.0:
|
||||
version "2.0.0"
|
||||
resolved "https://registry.yarnpkg.com/home-or-tmp/-/home-or-tmp-2.0.0.tgz#e36c3f2d2cae7d746a857e38d18d5f32a7882db8"
|
||||
integrity sha1-42w/LSyufXRqhX440Y1fMqeILbg=
|
||||
dependencies:
|
||||
os-homedir "^1.0.0"
|
||||
os-tmpdir "^1.0.1"
|
||||
|
||||
homedir-polyfill@^1.0.0, homedir-polyfill@^1.0.1:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/homedir-polyfill/-/homedir-polyfill-1.0.1.tgz#4c2bbc8a758998feebf5ed68580f76d46768b4bc"
|
||||
@@ -12169,7 +12223,7 @@ os-name@^3.0.0:
|
||||
macos-release "^2.0.0"
|
||||
windows-release "^3.1.0"
|
||||
|
||||
os-tmpdir@^1.0.0, os-tmpdir@~1.0.1, os-tmpdir@~1.0.2:
|
||||
os-tmpdir@^1.0.0, os-tmpdir@^1.0.1, os-tmpdir@~1.0.1, os-tmpdir@~1.0.2:
|
||||
version "1.0.2"
|
||||
resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274"
|
||||
integrity sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=
|
||||
@@ -12482,7 +12536,7 @@ path-exists@^3.0.0:
|
||||
resolved "https://registry.yarnpkg.com/path-exists/-/path-exists-3.0.0.tgz#ce0ebeaa5f78cb18925ea7d810d7b59b010fd515"
|
||||
integrity sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=
|
||||
|
||||
path-is-absolute@^1.0.0:
|
||||
path-is-absolute@^1.0.0, path-is-absolute@^1.0.1:
|
||||
version "1.0.1"
|
||||
resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f"
|
||||
integrity sha1-F0uSaHNVNP+8es5r9TpanhtcX18=
|
||||
@@ -13708,7 +13762,7 @@ punycode@^1.2.4, punycode@^1.4.1:
|
||||
resolved "https://registry.yarnpkg.com/punycode/-/punycode-1.4.1.tgz#c0d5a63b2718800ad8e1eb0fa5269c84dd41845e"
|
||||
integrity sha1-wNWmOycYgArY4esPpSachN1BhF4=
|
||||
|
||||
puppeteer@1.11.0, puppeteer@^1.11.0:
|
||||
puppeteer@^1.11.0:
|
||||
version "1.11.0"
|
||||
resolved "https://registry.yarnpkg.com/puppeteer/-/puppeteer-1.11.0.tgz#63cdbe12b07275cd6e0b94bce41f3fcb20305770"
|
||||
integrity sha512-iG4iMOHixc2EpzqRV+pv7o3GgmU2dNYEMkvKwSaQO/vMZURakwSOn/EYJ6OIRFYOque1qorzIBvrytPIQB3YzQ==
|
||||
@@ -14605,6 +14659,11 @@ schema-utils@^1.0.0:
|
||||
ajv-errors "^1.0.0"
|
||||
ajv-keywords "^3.1.0"
|
||||
|
||||
scrollparent@^2.0.1:
|
||||
version "2.0.1"
|
||||
resolved "https://registry.yarnpkg.com/scrollparent/-/scrollparent-2.0.1.tgz#715d5b9cc57760fb22bdccc3befb5bfe06b1a317"
|
||||
integrity sha1-cV1bnMV3YPsivczDvvtb/gaxoxc=
|
||||
|
||||
sec@^1.0.0:
|
||||
version "1.0.0"
|
||||
resolved "https://registry.yarnpkg.com/sec/-/sec-1.0.0.tgz#033d60a3ad20ecf2e00940d14f97823465774335"
|
||||
@@ -15005,6 +15064,13 @@ source-map-resolve@^0.5.0, source-map-resolve@^0.5.2:
|
||||
source-map-url "^0.4.0"
|
||||
urix "^0.1.0"
|
||||
|
||||
source-map-support@^0.4.15:
|
||||
version "0.4.18"
|
||||
resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.4.18.tgz#0286a6de8be42641338594e97ccea75f0a2c585f"
|
||||
integrity sha512-try0/JqxPLF9nOjvSta7tVondkP5dwgyLDjVoyMDlmjugT2lRZ1OfsrYTkCd2hkDnJTKRbO/Rl3orm8vlsUzbA==
|
||||
dependencies:
|
||||
source-map "^0.5.6"
|
||||
|
||||
source-map-support@^0.5.0, source-map-support@^0.5.6, source-map-support@~0.5.6, source-map-support@~0.5.9:
|
||||
version "0.5.10"
|
||||
resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.5.10.tgz#2214080bc9d51832511ee2bab96e3c2f9353120c"
|
||||
@@ -16591,6 +16657,11 @@ vue-apollo@^3.0.0-beta.25:
|
||||
chalk "^2.4.1"
|
||||
throttle-debounce "^2.0.0"
|
||||
|
||||
vue-class-component@^6.0.0:
|
||||
version "6.3.2"
|
||||
resolved "https://registry.yarnpkg.com/vue-class-component/-/vue-class-component-6.3.2.tgz#e6037e84d1df2af3bde4f455e50ca1b9eec02be6"
|
||||
integrity sha512-cH208IoM+jgZyEf/g7mnFyofwPDJTM/QvBNhYMjqGB8fCsRyTf68rH2ISw/G20tJv+5mIThQ3upKwoL4jLTr1A==
|
||||
|
||||
vue-class-component@^7.0.1:
|
||||
version "7.0.1"
|
||||
resolved "https://registry.yarnpkg.com/vue-class-component/-/vue-class-component-7.0.1.tgz#7af2225c600667c7042b60712eefdf41dfc6de63"
|
||||
@@ -16749,7 +16820,7 @@ vue-meta@^1.5.0:
|
||||
lodash.uniqueid "^4.0.1"
|
||||
object-assign "^4.1.1"
|
||||
|
||||
vue-observe-visibility@^0.4.1:
|
||||
vue-observe-visibility@^0.4.1, vue-observe-visibility@^0.4.3:
|
||||
version "0.4.3"
|
||||
resolved "https://registry.yarnpkg.com/vue-observe-visibility/-/vue-observe-visibility-0.4.3.tgz#b2694a83c94b274f566e03a497df51540e2daedc"
|
||||
integrity sha512-YyyO3a5OUkgpmC0NEf+xWJR0jVdFWzVbKRDzUumOVMhfr3+jxXEycYNHCM3rEO5lcj3ZNJpDomZEYEx0Wqqh9A==
|
||||
@@ -16776,7 +16847,7 @@ vue-router@^3.0.1, vue-router@^3.0.2:
|
||||
resolved "https://registry.yarnpkg.com/vue-router/-/vue-router-3.0.2.tgz#dedc67afe6c4e2bc25682c8b1c2a8c0d7c7e56be"
|
||||
integrity sha512-opKtsxjp9eOcFWdp6xLQPLmRGgfM932Tl56U9chYTnoWqKxQ8M20N7AkdEbM5beUh6wICoFGYugAX9vQjyJLFg==
|
||||
|
||||
vue-server-renderer@^2.5.16, vue-server-renderer@^2.6.7:
|
||||
vue-server-renderer@^2.5.16:
|
||||
version "2.6.7"
|
||||
resolved "https://registry.yarnpkg.com/vue-server-renderer/-/vue-server-renderer-2.6.7.tgz#ff40f69a439da8993a6e171b7d58575bfbeefb79"
|
||||
integrity sha512-CVtGR+bE63y4kyIeOcCEF2UNKquSquFQAsTHZ5R1cGM4L4Z0BXgAUEcngTOy8kN+tubt3c1zpRvbrok/bHKeDg==
|
||||
@@ -16823,6 +16894,15 @@ vue-timeago@^5.0.0:
|
||||
dependencies:
|
||||
date-fns "^1.29.0"
|
||||
|
||||
vue-virtual-scroller@^1.0.0-rc.2:
|
||||
version "1.0.0-rc.2"
|
||||
resolved "https://registry.yarnpkg.com/vue-virtual-scroller/-/vue-virtual-scroller-1.0.0-rc.2.tgz#b03828496c87889641bdacc75510e5b1bf5bda7f"
|
||||
integrity sha512-4YFx1a+QDP4f6HW/HBI/qHcmSTlh7BMH6IjEH8WC3ylt499cErl0LpvLLAx9yo3c6NtuK/XvjYXi0vvdxFB5dw==
|
||||
dependencies:
|
||||
scrollparent "^2.0.1"
|
||||
vue-observe-visibility "^0.4.3"
|
||||
vue-resize "^0.4.5"
|
||||
|
||||
vue@^2.5.16, vue@^2.6.6, vue@^2.6.7:
|
||||
version "2.6.7"
|
||||
resolved "https://registry.yarnpkg.com/vue/-/vue-2.6.7.tgz#254f188e7621d2d19ee28d0c0442c6d21b53ae2d"
|
||||
|
||||
Reference in New Issue
Block a user