fix: 无用代码、文件清理
This commit is contained in:
@@ -1,974 +0,0 @@
|
||||
.entity-detail-tool {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin: 10px 20px 10px 0;
|
||||
padding: 0 20px;
|
||||
height: 60px;
|
||||
background-color: #FFFFFF;
|
||||
box-shadow: 0 1px 2px 0 rgba(0,0,0,0.06);
|
||||
border-radius: 2px;
|
||||
|
||||
.cn-icon-arrow-left-circle {
|
||||
color: $--color-primary;
|
||||
font-size: 20px;
|
||||
}
|
||||
}
|
||||
|
||||
.chart-error-popper{
|
||||
word-wrap:break-word;
|
||||
word-break:break-word;
|
||||
border: 1px solid #e02f44;
|
||||
min-width: 180px !important;
|
||||
max-width: 280px !important;
|
||||
}
|
||||
|
||||
.chart-header-position{
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.chart-error-popper.el-popper.is-light {
|
||||
background: #e02f44;
|
||||
border: 1px solid #e02f44;
|
||||
}
|
||||
.chart-error-popper.el-popover.el-popper {
|
||||
color:white;
|
||||
}
|
||||
|
||||
.chart-error-popper.el-popper.is-light[data-popper-placement^='top'] .el-popper__arrow::before {
|
||||
border-color: #e02f44;
|
||||
background: #e02f44;
|
||||
bottom:0px;
|
||||
}
|
||||
|
||||
.chart-error-popper.el-popper.is-light[data-popper-placement^='bottom'] .el-popper__arrow::before {
|
||||
border-color: #e02f44;
|
||||
background: #e02f44;
|
||||
}
|
||||
|
||||
.chart-info-corner {
|
||||
color: #767980;
|
||||
cursor: pointer;
|
||||
position: absolute;
|
||||
display: none;
|
||||
left: 0;
|
||||
width: 28px;
|
||||
height: 28px;
|
||||
z-index: 2;
|
||||
top: 0;
|
||||
}
|
||||
.chart-info-corner--error {
|
||||
display: block;
|
||||
color: #fff;
|
||||
}
|
||||
.chart-info-corner--error .chart-info-corner-inner {
|
||||
border-left: 28px solid #e02f44;
|
||||
border-right: none;
|
||||
border-bottom: 28px solid rgba(0,0,0,0);
|
||||
}
|
||||
.chart-info-corner-inner {
|
||||
width: 0;
|
||||
height: 0;
|
||||
position: absolute;
|
||||
left: 0;
|
||||
bottom: 0;
|
||||
}
|
||||
.chart-info-corner .fa {
|
||||
position: absolute;
|
||||
top: 2px;
|
||||
left: 6px;
|
||||
font-size: 65%;
|
||||
z-index: 3;
|
||||
font-style: normal;
|
||||
}
|
||||
.cn-chart-icon-warning:before {
|
||||
content: "!";
|
||||
font-weight:normal;
|
||||
}
|
||||
|
||||
.cn-chart:not(.cn-chart__group):not(.cn-chart__block) {
|
||||
&>.cn-chart__body {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
.cn-panel, .cn-panel>.cn-chart__tabs>.el-tabs__content>.el-tab-pane, .cn-chart__group .cn-chart__body, .cn-chart__block .cn-chart__body {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(30, 1fr);
|
||||
grid-auto-flow: row;
|
||||
grid-gap: 10px;
|
||||
overflow: auto;
|
||||
padding-right: 20px;
|
||||
position: relative;
|
||||
|
||||
.panel__time {
|
||||
position: absolute;
|
||||
right: 20px;
|
||||
top: 10px;
|
||||
z-index: 1;
|
||||
display: flex;
|
||||
|
||||
&>div {
|
||||
margin-left: 10px;
|
||||
}
|
||||
}
|
||||
|
||||
&>.cn-chart {
|
||||
position: relative;
|
||||
background-color: #FFFFFF;
|
||||
border: 1px solid #E7EAED;
|
||||
box-shadow: 0 2px 4px 0 rgba(51,51,51,0.02);
|
||||
border-radius: 2px;
|
||||
height: calc(100% - 47px);
|
||||
width: 100%;
|
||||
|
||||
.chart-drawing {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
&>.cn-chart__whois>.cn-chart__body {
|
||||
overflow: auto;
|
||||
}
|
||||
&>.cn-chart__echarts, &>.cn-chart__table, &>.cn-chart__map, &>.cn-chart__group, &>.cn-chart__block, &>.cn-chart__whois, &>.cn-chart__dns-record, &>.cn-chart__app-basic {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
.cn-chart__header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
flex-shrink: 0;
|
||||
padding: 10px 20px 10px 18px;
|
||||
height: 47px;
|
||||
|
||||
.cn-chart__title {
|
||||
font-size: 16px;
|
||||
color: #333333;
|
||||
font-weight: bold;
|
||||
}
|
||||
.header__operations {
|
||||
color: #999;
|
||||
}
|
||||
}
|
||||
.cn-chart__body {
|
||||
flex: auto;
|
||||
display: flex;
|
||||
.el-descriptions {
|
||||
padding-top: 30px;
|
||||
}
|
||||
&>.el-descriptions {
|
||||
flex: 0 0 350px;
|
||||
padding: 30px 36px;
|
||||
}
|
||||
.chart-location {
|
||||
display: flex;
|
||||
flex: 1;
|
||||
flex-direction: column;
|
||||
padding: 0 20px 20px 0;
|
||||
}
|
||||
.el-descriptions__content {
|
||||
color: #3976CB;
|
||||
}
|
||||
}
|
||||
}
|
||||
&>.cn-chart__block {
|
||||
&>.cn-chart__header {
|
||||
height: 60px;
|
||||
border-bottom: none !important;
|
||||
}
|
||||
&>.cn-chart__body {
|
||||
display: grid !important;
|
||||
grid-template-columns: repeat(30, 1fr);
|
||||
grid-auto-flow: row;
|
||||
grid-gap: 10px;
|
||||
padding: 0 20px;
|
||||
&>.cn-chart {
|
||||
border: 1px solid #E7EAED;
|
||||
}
|
||||
/* detail页面block下的五连图的标题样式改变 */
|
||||
.cn-chart__group .cn-chart__echarts {
|
||||
.cn-chart__header {
|
||||
border-bottom: none !important;
|
||||
|
||||
.header__title {
|
||||
font-size: 14px !important;
|
||||
color: #3976CB !important;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.cn-chart__group {
|
||||
.cn-chart__header {
|
||||
border-bottom: 1px solid $--content-right-background-color;
|
||||
}
|
||||
&>.cn-chart__body {
|
||||
display: grid !important;
|
||||
grid-gap: 10px;
|
||||
padding: 0 20px;
|
||||
.cn-chart {
|
||||
border: none;
|
||||
box-shadow: none;
|
||||
}
|
||||
}
|
||||
}
|
||||
&>.cn-chart__title {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
font-size: 20px;
|
||||
padding-left: 10px;
|
||||
color: #333;
|
||||
background-color: transparent;
|
||||
box-shadow: none;
|
||||
border: none;
|
||||
}
|
||||
&>.cn-chart__tabs {
|
||||
padding: 10px 25px 10px 15px;
|
||||
|
||||
.el-tabs__nav-wrap::after {
|
||||
height: 1px;
|
||||
}
|
||||
&>.el-tabs__header {
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
&>.el-tabs__content {
|
||||
height: calc(100% - 40px);
|
||||
}
|
||||
}
|
||||
&>.cn-chart__table {
|
||||
.cn-chart__header {
|
||||
border-bottom: 1px solid $--content-right-background-color;
|
||||
.header__operations {
|
||||
display: flex;
|
||||
justify-content: end;
|
||||
align-items: center;
|
||||
|
||||
.header__operation.header__operation--table {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 22px;
|
||||
margin-left: 10px;
|
||||
color: $--color-primary;
|
||||
border: 1px solid $--color-primary;
|
||||
border-radius: $--border-radius-primary;
|
||||
|
||||
.option__button {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 100%;
|
||||
padding: 0 5px;
|
||||
cursor: pointer;
|
||||
background-color: white;
|
||||
transition: all linear .2s;
|
||||
}
|
||||
.option__button:hover {
|
||||
background-color: #EFF2F5;
|
||||
}
|
||||
.option__button.icon-group-item:first-of-type:not(:last-of-type) {
|
||||
padding: 0 5px 0 0;
|
||||
}
|
||||
.option__button.icon-group-item:last-of-type:not(:first-of-type) {
|
||||
padding: 0 0 0 5px;
|
||||
}
|
||||
.option__select {
|
||||
.el-input__inner {
|
||||
width: 80px;
|
||||
padding-right: 20px;
|
||||
border: none;
|
||||
height: 100%;
|
||||
line-height: 20px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
.el-input__prefix > div {
|
||||
font-weight: normal;
|
||||
line-height: 19px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
.el-input__suffix {
|
||||
display: flex;
|
||||
.el-input__suffix-inner {
|
||||
line-height: 14px;
|
||||
.el-select__caret {
|
||||
line-height: 14px;
|
||||
width: 16px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.option__select.select-column {
|
||||
.el-input__inner {
|
||||
width: 86px;
|
||||
padding-left: 8px;
|
||||
}
|
||||
}
|
||||
.icon-group-divide {
|
||||
height: 14px;
|
||||
width: 1px;
|
||||
background-color: $--color-primary;
|
||||
}
|
||||
i {
|
||||
font-size: 12px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.cn-chart__body {
|
||||
flex: auto;
|
||||
overflow-y: auto;
|
||||
|
||||
.el-table {
|
||||
padding: 0 10px;
|
||||
|
||||
&:before {
|
||||
height: 0;
|
||||
}
|
||||
thead {
|
||||
color: #333;
|
||||
}
|
||||
th.is-leaf, td {
|
||||
border-bottom: none;
|
||||
}
|
||||
th {
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
td {
|
||||
padding: 4px 0;
|
||||
color: #333;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
&>.cn-chart__echarts {
|
||||
.cn-chart__header {
|
||||
border-bottom: 1px solid $--content-right-background-color;
|
||||
.header__operations {
|
||||
display: flex;
|
||||
justify-content: end;
|
||||
align-items: center;
|
||||
|
||||
.header__operation.header__operation--echarts {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 22px;
|
||||
margin-left: 10px;
|
||||
color: $--color-primary;
|
||||
border: 1px solid $--color-primary;
|
||||
border-radius: $--border-radius-primary;
|
||||
|
||||
.option__button {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 100%;
|
||||
padding: 0 5px;
|
||||
cursor: pointer;
|
||||
background-color: white;
|
||||
transition: all linear .2s;
|
||||
}
|
||||
.option__button:hover {
|
||||
background-color: #EFF2F5;
|
||||
}
|
||||
.option__button.icon-group-item:first-of-type:not(:last-of-type) {
|
||||
padding: 0 5px 0 0;
|
||||
}
|
||||
.option__button.icon-group-item:last-of-type:not(:first-of-type) {
|
||||
padding: 0 0 0 5px;
|
||||
}
|
||||
.option__select {
|
||||
.el-input__inner {
|
||||
width: 120px;
|
||||
padding-right: 20px;
|
||||
border: none;
|
||||
height: 100%;
|
||||
line-height: 20px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
.el-input__prefix > div {
|
||||
font-weight: normal;
|
||||
line-height: 19px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
.el-input__suffix {
|
||||
display: flex;
|
||||
.el-input__suffix-inner {
|
||||
line-height: 14px;
|
||||
.el-select__caret {
|
||||
line-height: 14px;
|
||||
width: 16px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.option__select.select-column {
|
||||
.el-input__inner {
|
||||
width: 86px;
|
||||
padding-left: 8px;
|
||||
}
|
||||
}
|
||||
.icon-group-divide {
|
||||
height: 14px;
|
||||
width: 1px;
|
||||
background-color: $--color-primary;
|
||||
}
|
||||
i {
|
||||
font-size: 12px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
.cn-chart__body {
|
||||
overflow: hidden auto;
|
||||
|
||||
.el-table {
|
||||
padding: 0 10px;
|
||||
|
||||
&:before {
|
||||
height: 0;
|
||||
}
|
||||
thead {
|
||||
color: #333;
|
||||
}
|
||||
th.is-leaf, td {
|
||||
border-bottom: none;
|
||||
}
|
||||
th {
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
td {
|
||||
padding: 4px 0;
|
||||
color: #333;
|
||||
}
|
||||
}
|
||||
}
|
||||
.cn-chart__body.pie-with-table {
|
||||
flex-basis: 40%;
|
||||
}
|
||||
.cn-chart__footer.pie-with-table {
|
||||
flex-basis: 60%;
|
||||
padding: 10px 30px 30px;
|
||||
}
|
||||
}
|
||||
.pie-table {
|
||||
font-size: 14px;
|
||||
color: #333333;
|
||||
font-weight: 500;
|
||||
|
||||
.el-table__header-wrapper {
|
||||
.cell {
|
||||
color: #333;
|
||||
}
|
||||
}
|
||||
.el-table__expanded-cell[class*=cell] {
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.expand-table .el-table__body .el-table__row:last-of-type td {
|
||||
border: none;
|
||||
}
|
||||
.expand-table {
|
||||
font-weight: 400;
|
||||
color: #606266;
|
||||
|
||||
.el-table__body-wrapper {
|
||||
height: auto !important;
|
||||
}
|
||||
}
|
||||
}
|
||||
.chart__legend {
|
||||
width: calc(100% - 40px);
|
||||
border: 1px solid #E7EAED;
|
||||
color: #5f6368;
|
||||
margin: auto;
|
||||
margin-bottom: 15px;
|
||||
|
||||
.chart__table-top {
|
||||
width: 100%;
|
||||
height: 30px;
|
||||
border-bottom: #E7EAED 1px solid;
|
||||
display: flex;
|
||||
|
||||
div {
|
||||
font-size: 13px;
|
||||
line-height: 28px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
}
|
||||
.chart__table-below {
|
||||
height: 240px;
|
||||
width: 100%;
|
||||
font-size: 13px;
|
||||
}
|
||||
.table-below-box {
|
||||
width: 100%;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
line-height: 24px;
|
||||
}
|
||||
.table-below-box:hover {
|
||||
background-color: #f9f9f9;
|
||||
border: 0;
|
||||
color: #383838;
|
||||
}
|
||||
.table__below-color {
|
||||
width: 27px;
|
||||
height: 7px;
|
||||
flex-shrink: 0;
|
||||
padding-left: 10px;
|
||||
|
||||
div {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
border-radius: 24%;
|
||||
}
|
||||
}
|
||||
.table__below-title {
|
||||
padding: 0 6px;
|
||||
flex-shrink: 1;
|
||||
flex-grow: 1;
|
||||
overflow: hidden;
|
||||
min-width: 200px;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.table__below-statistics {
|
||||
width: 80px;
|
||||
flex-shrink: 0;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.table-below-box:not(.chart__table-top) {
|
||||
cursor: pointer;
|
||||
}
|
||||
.table-below-box.table-below-box--inactivated {
|
||||
color: #ccc;
|
||||
.table__below-color div {
|
||||
background-color: #ccc !important;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@media only screen and (min-width : 10px) {
|
||||
.cn-panel, .cn-panel>.cn-chart__tabs>.el-tabs__content>.el-tab-pane,
|
||||
.cn-chart__body {
|
||||
grid-auto-rows: 25px;
|
||||
}
|
||||
}
|
||||
@media only screen and (min-width : 1224px) {
|
||||
.cn-panel,
|
||||
.cn-panel>.cn-chart__tabs>.el-tabs__content>.el-tab-pane,
|
||||
.cn-chart__body {
|
||||
grid-auto-rows: 30px;
|
||||
}
|
||||
}
|
||||
@media only screen and (min-width : 1824px) {
|
||||
.cn-panel,
|
||||
.cn-panel>.cn-chart__tabs>.el-tabs__content>.el-tab-pane,
|
||||
.cn-chart__body {
|
||||
grid-auto-rows: 40px;
|
||||
}
|
||||
}
|
||||
@media only screen and (min-width : 2424px) {
|
||||
.cn-panel,
|
||||
.cn-panel>.cn-chart__tabs>.el-tabs__content>.el-tab-pane,
|
||||
.cn-chart__body {
|
||||
grid-auto-rows: 55px;
|
||||
}
|
||||
}
|
||||
.cn-panel>.cn-chart__tabs>.el-tabs__content>.el-tab-pane>.cn-chart {
|
||||
border: none;
|
||||
box-shadow: none;
|
||||
.cn-chart__header {
|
||||
border-bottom: none;
|
||||
}
|
||||
}
|
||||
|
||||
.cn-entity-detail {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
overflow: hidden;
|
||||
.entity-detail__header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
height: 70px;
|
||||
padding-right: 20px;
|
||||
background-color: #F7F9FB;
|
||||
|
||||
.detail-header__title {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
padding-left: 20px;
|
||||
font-size: 20px;
|
||||
|
||||
.title__icon-circle {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
height: 38px;
|
||||
width: 38px;
|
||||
border-radius: 50%;
|
||||
background-color: #B8C1D1;
|
||||
|
||||
i {
|
||||
color: white;
|
||||
font-size: 20px;
|
||||
}
|
||||
}
|
||||
.title__name {
|
||||
text-overflow: ellipsis;
|
||||
max-width: 400px;
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
padding-left: 10px;
|
||||
color: #333;
|
||||
}
|
||||
}
|
||||
.detail-header__operation {
|
||||
display: flex;
|
||||
align-items: flex-end;
|
||||
|
||||
.panel__time {
|
||||
display: flex;
|
||||
padding: 0 30px 10px 0;
|
||||
}
|
||||
|
||||
& > .el-tabs > .el-tabs__header { // header背景色
|
||||
margin: 0 0 -1px 0;
|
||||
|
||||
& > .el-tabs__nav-wrap > .el-tabs__nav-scroll > .el-tabs__nav {
|
||||
& > .el-tabs__item {
|
||||
height: 35px;
|
||||
line-height: 35px;
|
||||
}
|
||||
& > .el-tabs__item.is-active { // 激活的tab上边框和背景色
|
||||
background-color: white;
|
||||
border-top: 2px solid #0091ff;
|
||||
}
|
||||
& > .el-tabs__active-bar {
|
||||
display: none;
|
||||
}
|
||||
& > div:last-of-type {
|
||||
padding-right: 20px;
|
||||
}
|
||||
& > div:nth-of-type(2) {
|
||||
padding-left: 20px;
|
||||
}
|
||||
}
|
||||
}
|
||||
& > .el-tabs > .el-tabs__header > .el-tabs__nav-wrap::after { // 去掉tabs下方边框
|
||||
height: 0 !important;
|
||||
}
|
||||
&>.el-tabs { // 底部对齐
|
||||
display: flex;
|
||||
align-items: flex-end;
|
||||
}
|
||||
}
|
||||
}
|
||||
.entity-detail__body {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
overflow: auto;
|
||||
/*&>div {
|
||||
display: grid;
|
||||
grid-template-columns: repeat(30, 1fr);
|
||||
grid-auto-flow: row;
|
||||
grid-gap: 10px;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.cn-panel {
|
||||
padding: 20px;
|
||||
grid-gap: 10px;
|
||||
|
||||
&>.cn-chart>.cn-chart__header {
|
||||
border-bottom: 1px solid $--content-right-background-color;
|
||||
.header__title>span {
|
||||
color: #1890FF;
|
||||
font-weight: bold;
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
&>.cn-chart>.cn-chart__body {
|
||||
.cn-chart__header {
|
||||
border-bottom: 1px solid $--content-right-background-color;
|
||||
.header__title {
|
||||
color: #666;
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}*/
|
||||
}
|
||||
}
|
||||
.el-overlay {
|
||||
overflow: hidden !important;
|
||||
}
|
||||
.entity-detail__dialog {
|
||||
height: 90vh;
|
||||
overflow: hidden;
|
||||
.el-dialog__header {
|
||||
display: none;
|
||||
}
|
||||
.el-dialog__body {
|
||||
height: 100%;
|
||||
padding: 0;
|
||||
}
|
||||
}
|
||||
.option-popper {
|
||||
.el-select-dropdown__item {
|
||||
height: 24px;
|
||||
line-height: 24px;
|
||||
font-size: 12px;
|
||||
}
|
||||
}
|
||||
.header__operation-btn {
|
||||
margin-left: 12px;
|
||||
cursor: pointer;
|
||||
color: #999;
|
||||
}
|
||||
.ip-detail-as {
|
||||
color: #999;
|
||||
font-size: 12px;
|
||||
padding-left: 10px;
|
||||
}
|
||||
//.cn-chart-select{
|
||||
// display: flex;
|
||||
// align-items: center;
|
||||
// height: 22px;
|
||||
// margin-left: 10px;
|
||||
// color: #0091ff;
|
||||
// border: 1px solid #0091ff;
|
||||
// border-radius: 2px;
|
||||
//}
|
||||
.cn-chart__single-value.cn-chart__single-value--detail-overview.cn-chart__single-value--icon-left {
|
||||
.single-value__icon {
|
||||
width: 38px;
|
||||
height: 38px;
|
||||
|
||||
i {
|
||||
font-size: 15px;
|
||||
}
|
||||
}
|
||||
.single-value__content {
|
||||
.content__data {
|
||||
font-size: 14px;
|
||||
}
|
||||
.content__title {
|
||||
font-size: 12px;
|
||||
}
|
||||
}
|
||||
}
|
||||
.cn-chart__single-value.cn-chart__single-value--icon-left {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
|
||||
.single-value-icon__box {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
flex: 0 0 40%;
|
||||
}
|
||||
|
||||
.single-value__icon {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
width: 72px;
|
||||
height: 72px;
|
||||
background-color: $--chart-single-value-icon-background-color;
|
||||
border-radius: 50%;
|
||||
|
||||
i {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
font-size: 28px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
}
|
||||
|
||||
.single-value__content {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
max-width: 60%;
|
||||
padding-right: 10px;
|
||||
|
||||
.content__data {
|
||||
padding-bottom: 7%;
|
||||
font-size: 24px;
|
||||
color: #333333;
|
||||
font-weight: bold;
|
||||
}
|
||||
.content__title {
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
text-overflow: ellipsis;
|
||||
font-size: 16px;
|
||||
color: #666666;
|
||||
}
|
||||
&.single-value__content--with-chart {
|
||||
.content__title {
|
||||
border-bottom: 1px solid $--content-right-background-color;
|
||||
}
|
||||
}
|
||||
.single-value__unit {
|
||||
font-weight: normal;
|
||||
padding-left: 10px;
|
||||
color: #666;
|
||||
font-size: 20px;
|
||||
}
|
||||
}
|
||||
}
|
||||
.cn-chart__single-value.cn-chart__single-value--icon-right {
|
||||
display: flex;
|
||||
flex-direction: row-reverse;
|
||||
justify-content: space-around;
|
||||
align-items: center;
|
||||
|
||||
.single-value__icon {
|
||||
background-color: $--chart-single-value-icon-background-color;
|
||||
border-radius: 50%;
|
||||
position: relative;
|
||||
margin-right: 7.5%;
|
||||
margin-bottom: 6%;
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
|
||||
i {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
transform: translate(-50%,-50%);
|
||||
font-size: 24px;
|
||||
color: $--color-primary;
|
||||
}
|
||||
}
|
||||
|
||||
.single-value__content {
|
||||
display: flex;
|
||||
height: 100%;
|
||||
flex-direction: column;
|
||||
|
||||
.content__title {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 50%;
|
||||
font-size: 16px;
|
||||
color: #666666;
|
||||
}
|
||||
.content__data {
|
||||
display: flex;
|
||||
padding-top: 5%;
|
||||
height: 50%;
|
||||
flex: auto;
|
||||
font-size: 24px;
|
||||
color: #333333;
|
||||
font-weight: bold;
|
||||
}
|
||||
}
|
||||
}
|
||||
.cn-chart__single-value.cn-chart__single-value--icon-right--color {
|
||||
display: flex;
|
||||
flex-direction: row-reverse;
|
||||
justify-content: space-around;
|
||||
align-items: center;
|
||||
|
||||
.single-value__content {
|
||||
display: flex;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
flex-direction: row-reverse;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
|
||||
.single-value-icon__box {
|
||||
padding-right: 30px;
|
||||
.single-value__icon {
|
||||
border-radius: 50%;
|
||||
position: relative;
|
||||
margin-right: 7.5%;
|
||||
margin-top: 30%;
|
||||
|
||||
.cn-icon-svg {
|
||||
width: 50px;
|
||||
height: 50px;
|
||||
vertical-align: middle;
|
||||
fill: currentColor;
|
||||
overflow: hidden;
|
||||
}
|
||||
|
||||
i {
|
||||
position: absolute;
|
||||
top: 50%;
|
||||
left: 50%;
|
||||
transform: translate(-50%,-50%);
|
||||
font-size: 24px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.single-value__data{
|
||||
display: flex;
|
||||
height: 100%;
|
||||
flex-direction: column;
|
||||
padding-left: 20px;
|
||||
|
||||
.content__title {
|
||||
display: flex;
|
||||
align-items: end;
|
||||
height: 50%;
|
||||
font-size: 16px;
|
||||
color: #666666;
|
||||
padding-bottom: 5px;
|
||||
}
|
||||
.content__data {
|
||||
display: flex;
|
||||
padding-top: 5%;
|
||||
height: 50%;
|
||||
flex: auto;
|
||||
font-size: 24px;
|
||||
color: #333333;
|
||||
font-weight: bold;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
.cn-chart__single-value.cn-chart__single-value--chart {
|
||||
display: flex;
|
||||
padding: 13px 20px;
|
||||
|
||||
.single-value__content {
|
||||
display: flex;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
flex-direction: column;
|
||||
|
||||
.content__title {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 30%;
|
||||
font-size: 16px;
|
||||
color: #666666;
|
||||
}
|
||||
.content__data {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
height: 25%;
|
||||
font-size: 24px;
|
||||
color: #333333;
|
||||
font-weight: bold;
|
||||
}
|
||||
.content__chart {
|
||||
flex: auto
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.chart-table-pagination.el-pagination {
|
||||
padding: 12px 0 9px 0;
|
||||
text-align: center;
|
||||
|
||||
.el-pagination__jump {
|
||||
margin-left: 10px;
|
||||
}
|
||||
}
|
||||
@@ -1,39 +0,0 @@
|
||||
<template>
|
||||
<div class="cn-chart__map">
|
||||
<div class="cn-chart__header chart-header-position" >
|
||||
<slot name="chartErrorInfo"></slot>
|
||||
<div class="header__title" v-if="!hideHeader">
|
||||
<slot name="title"></slot>
|
||||
</div>
|
||||
<div class="header__operations" v-if="!hideHeader">
|
||||
<slot name="operations"></slot>
|
||||
</div>
|
||||
</div>
|
||||
<div class="cn-chart__body">
|
||||
<slot></slot>
|
||||
</div>
|
||||
<div class="chart__loading" v-show="loading">
|
||||
<i class="el-icon-loading"></i>
|
||||
</div>
|
||||
<div class="cn-chart__footer">
|
||||
<slot name="footer"></slot>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
|
||||
export default {
|
||||
name: 'ChartMap',
|
||||
props: {
|
||||
loading: Boolean,
|
||||
hideHeader: Boolean
|
||||
},
|
||||
data () {
|
||||
return {
|
||||
errorContent: '出错了。。。',
|
||||
isError: true
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -1,95 +0,0 @@
|
||||
<template>
|
||||
<div class="cn-chart cn-chart__single-value chart-header-position" :class="singleValueClass(type)" :style="{backgroundColor:color}">
|
||||
<slot name="chartErrorInfo"></slot>
|
||||
<div class="single-value-icon__box" v-if="type != 54">
|
||||
<div class="single-value__icon"><i :class="icon"></i></div>
|
||||
</div>
|
||||
<div class="chart__loading" v-show="loading">
|
||||
<i class="el-icon-loading"></i>
|
||||
</div>
|
||||
<div class="single-value__content" v-if="type === 51">
|
||||
<div class="content__data">
|
||||
<slot name="data"></slot>
|
||||
</div>
|
||||
<div class="content__title">
|
||||
<slot name="title"></slot>
|
||||
</div>
|
||||
</div>
|
||||
<div class="single-value__content single-value__content--with-chart" v-if="type === 52 || type === 55">
|
||||
<div class="content__title">
|
||||
<slot name="title"></slot>
|
||||
</div>
|
||||
<div class="content__data">
|
||||
<slot name="data"></slot>
|
||||
</div>
|
||||
<div class="content__chart">
|
||||
<slot name="chart"></slot>
|
||||
</div>
|
||||
</div>
|
||||
<div class="single-value__content" v-if="type === 53">
|
||||
<div class="content__title"></div>
|
||||
<div class="content__data"></div>
|
||||
</div>
|
||||
<div class="single-value__content" v-if="type === 54" >
|
||||
<div class="single-value-icon__box" >
|
||||
<div class="single-value__icon">
|
||||
<!-- 使用图标-->
|
||||
<svg class="cn-icon-svg" aria-hidden="true">
|
||||
<use :xlink:href="icon"></use>
|
||||
</svg>
|
||||
</div>
|
||||
</div>
|
||||
<div class="single-value__data">
|
||||
<div class="content__title">
|
||||
<slot name="title"></slot>
|
||||
</div>
|
||||
<div class="content__data">
|
||||
<slot name="data"></slot>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import '@/assets/css/font/iconfont.js'
|
||||
|
||||
export default {
|
||||
name: 'ChartSingleValue',
|
||||
props: {
|
||||
type: Number,
|
||||
icon: String,
|
||||
loading: Boolean,
|
||||
color: String
|
||||
},
|
||||
computed: {
|
||||
singleValueClass () {
|
||||
return function (type) {
|
||||
let c
|
||||
switch (type) {
|
||||
case 51: {
|
||||
c = 'cn-chart__single-value--icon-left'
|
||||
break
|
||||
}
|
||||
case 55:
|
||||
case 52: {
|
||||
c = 'cn-chart__single-value--chart'
|
||||
break
|
||||
}
|
||||
case 53: {
|
||||
c = 'cn-chart__single-value--icon-right'
|
||||
break
|
||||
}
|
||||
case 54: {
|
||||
c = 'cn-chart__single-value--icon-right--color'
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
return c
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -1,72 +0,0 @@
|
||||
<template>
|
||||
<div class="cn-chart cn-chart__table">
|
||||
<div class="cn-chart__header chart-header-position" >
|
||||
<slot name="chartErrorInfo"></slot>
|
||||
<div class="header__title">
|
||||
<slot name="title"></slot>
|
||||
</div>
|
||||
<div class="header__operations">
|
||||
<slot name="operations"></slot>
|
||||
</div>
|
||||
</div>
|
||||
<div class="chart__loading" v-show="loading">
|
||||
<i class="el-icon-loading"></i>
|
||||
</div>
|
||||
<div class="cn-chart__body" v-no-data="noData">
|
||||
<el-table
|
||||
style="width: 100%"
|
||||
tooltip-effect="light"
|
||||
:data="tableData"
|
||||
>
|
||||
<el-table-column
|
||||
type="index"
|
||||
label="#"
|
||||
>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
v-for="(c, i) in tableColumns"
|
||||
show-overflow-tooltip
|
||||
:key="i"
|
||||
:label="c.label"
|
||||
:prop="c.prop"
|
||||
>
|
||||
<template #header>{{c.label}}</template>
|
||||
<template #default="{ row }">{{}}
|
||||
<span v-if="c.prop === 'bytes'">
|
||||
{{unitConvert(row[c.prop], unitTypes.byte).join(' ')}}
|
||||
</span>
|
||||
<span v-else-if="c.prop === 'packets' || c.prop === 'sessions'">
|
||||
{{unitConvert(row[c.prop], unitTypes.number).join(' ')}}
|
||||
</span>
|
||||
<span v-else>
|
||||
{{row[c.prop]}}
|
||||
</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
<div class="cn-chart__footer">
|
||||
<slot name="footer"></slot>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
export default {
|
||||
name: 'ChartTable',
|
||||
props: {
|
||||
tableColumns: Array,
|
||||
tableData: Array,
|
||||
loading: Boolean,
|
||||
noData: Boolean
|
||||
},
|
||||
setup () {
|
||||
return {
|
||||
unitTypes,
|
||||
unitConvert
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -1,112 +0,0 @@
|
||||
<template>
|
||||
<div class="cn-chart cn-chart__table">
|
||||
<div class="cn-chart__header chart-header-position" >
|
||||
<slot name="chartErrorInfo"></slot>
|
||||
<div class="header__title ">
|
||||
<slot name="title"></slot>
|
||||
</div>
|
||||
<div class="header__operations">
|
||||
<slot name="operations"></slot>
|
||||
</div>
|
||||
</div>
|
||||
<div class="chart__loading" v-show="loading">
|
||||
<i class="el-icon-loading"></i>
|
||||
</div>
|
||||
<div class="cn-chart__body" v-no-data="noData">
|
||||
<el-table
|
||||
style="width: 100%"
|
||||
tooltip-effect="light"
|
||||
:data="tableData"
|
||||
:show-header="false"
|
||||
:cell-style="{padding:'7px 0'}"
|
||||
>
|
||||
<el-table-column>
|
||||
<template #default="{ row }">
|
||||
<div class="active-ip__icon"><i class="cn-icon cn-icon-ip ip-green"></i></div>
|
||||
<div class="active-ip__content" >
|
||||
{{row['name']}}
|
||||
</div>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column align="center">
|
||||
<template #default="{ row }">
|
||||
<span>
|
||||
{{row['num']}}
|
||||
</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
|
||||
<el-table-column
|
||||
v-for="(c, i) in tableColumns"
|
||||
show-overflow-tooltip
|
||||
:key="i"
|
||||
:label="c.label"
|
||||
:prop="c.prop"
|
||||
>
|
||||
<template #default="{ row }">
|
||||
<span v-if="c.prop === 'bytes'">
|
||||
{{unitConvert(row[c.prop], unitTypes.byte).join(' ')}}
|
||||
</span>
|
||||
<span v-else-if="c.prop === 'packets' || c.prop === 'sessions'">
|
||||
{{unitConvert(row[c.prop], unitTypes.number).join(' ')}}
|
||||
</span>
|
||||
<span v-else>
|
||||
{{row[c.prop]}}
|
||||
</span>
|
||||
</template>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
<div class="cn-chart__footer">
|
||||
<slot name="footer"></slot>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
export default {
|
||||
name: 'ChartTableActiveIp',
|
||||
props: {
|
||||
tableColumns: Array,
|
||||
tableData: Array,
|
||||
loading: Boolean,
|
||||
noData: Boolean
|
||||
},
|
||||
setup () {
|
||||
return {
|
||||
unitTypes,
|
||||
unitConvert
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style>
|
||||
|
||||
.active-ip__icon {
|
||||
overflow: hidden;
|
||||
position: absolute;
|
||||
top: 8px;
|
||||
left: 6px;
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
justify-items: center;
|
||||
align-items: center;
|
||||
width: 23px;
|
||||
height: 23px;
|
||||
border-radius: 50%;
|
||||
background: #e8fbf9;
|
||||
border: 2px solid #e8fbf9;
|
||||
}
|
||||
.ip-green {
|
||||
color: #23BF9A;
|
||||
}
|
||||
.active-ip__content {
|
||||
position: absolute;
|
||||
top: 7px;
|
||||
left: 35px;
|
||||
overflow: hidden;
|
||||
}
|
||||
</style>
|
||||
@@ -1,55 +0,0 @@
|
||||
<template>
|
||||
<el-pagination
|
||||
small
|
||||
ref="pagination"
|
||||
layout="prev,jumper,slot,next"
|
||||
class="chart-table-pagination"
|
||||
:total="total"
|
||||
:page-size="pageSize"
|
||||
v-model:currentPage="pageNo"
|
||||
@current-change="current"
|
||||
>
|
||||
<span>/ {{totalPage}}</span>
|
||||
</el-pagination>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { chartTableDefaultPageSize } from '@/utils/constants'
|
||||
export default {
|
||||
name: 'ChartTablePagination',
|
||||
props: {
|
||||
total: Number
|
||||
},
|
||||
data () {
|
||||
return {
|
||||
pageSize: chartTableDefaultPageSize,
|
||||
pageNo: 1
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
totalPage () {
|
||||
const remainder = this.total % this.pageSize
|
||||
if (remainder) {
|
||||
return parseInt(this.total / this.pageSize) + 1
|
||||
} else {
|
||||
return parseInt(this.total / this.pageSize)
|
||||
}
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
current (val) {
|
||||
this.$emit('pageJump', val)
|
||||
},
|
||||
resetPageNo () {
|
||||
this.pageNo = 1
|
||||
}
|
||||
},
|
||||
mounted () {
|
||||
const _this = this
|
||||
this.emitter.on('chart-pageNo', function () {
|
||||
_this.resetPageNo()
|
||||
})
|
||||
this.$el.querySelector('.el-pagination__jump').childNodes[0].nodeValue = ''
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -1,9 +0,0 @@
|
||||
<template>
|
||||
<div class="cn-chart cn-chart__title"></div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name: 'ChartTitle'
|
||||
}
|
||||
</script>
|
||||
@@ -1,44 +0,0 @@
|
||||
<template>
|
||||
<div class="cn-chart cn-chart__echarts" :class="{'cn-chart__echarts--statistics': isEchartsWithStatistics}">
|
||||
<div class="cn-chart__header chart-header-position" v-if="layout.indexOf(layoutConstant.HEADER) > -1" >
|
||||
<slot name="chartErrorInfo"></slot>
|
||||
<div class="header__title">
|
||||
<slot name="title"></slot>
|
||||
</div>
|
||||
<div class="header__operations">
|
||||
<slot name="operations"></slot>
|
||||
</div>
|
||||
</div>
|
||||
<div class="cn-chart__body" :class="{'pie-with-table': isPieWithTable}" v-no-data="noData">
|
||||
<slot></slot>
|
||||
</div>
|
||||
<div class="chart__loading" v-show="loading">
|
||||
<i class="el-icon-loading"></i>
|
||||
</div>
|
||||
<div class="cn-chart__footer" v-if="layout.indexOf(layoutConstant.FOOTER) > -1 && !noData" :class="{'pie-with-table': isPieWithTable}">
|
||||
<slot name="footer"></slot>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { layoutConstant, isEchartsWithTable, isEchartsWithStatistics } from '@/components/charts/chart-options'
|
||||
export default {
|
||||
name: 'EchartsFrame',
|
||||
props: {
|
||||
layout: Array,
|
||||
chartInfo: Object,
|
||||
loading: Boolean,
|
||||
noData: Boolean
|
||||
},
|
||||
setup (props) {
|
||||
return {
|
||||
layoutConstant,
|
||||
isPieWithTable: isEchartsWithTable(props.chartInfo.type),
|
||||
isEchartsWithStatistics: isEchartsWithStatistics(props.chartInfo.type)
|
||||
}
|
||||
},
|
||||
mounted () {
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -1,258 +0,0 @@
|
||||
<template>
|
||||
<el-table
|
||||
ref="table"
|
||||
class="pie-table"
|
||||
:data="pieTableData"
|
||||
style="width: 100%;border: 1px solid #E7EAED"
|
||||
:row-key="getRowKey"
|
||||
@expand-change="currentChange"
|
||||
:current-row-key="tableNameColumn"
|
||||
tooltip-effect="light"
|
||||
:expand-row-keys="expandRowKeys"
|
||||
size="mini"
|
||||
height="100%">
|
||||
<el-table-column type="expand" min-width="5%">
|
||||
<template #default="props">
|
||||
<div style="position: relative">
|
||||
<div class="chart__loading" style="top: 0; height: 100%; z-index: 1;" v-show="loading">
|
||||
<i class="el-icon-loading"></i>
|
||||
</div>
|
||||
<el-table
|
||||
tooltip-effect="light"
|
||||
class="expand-table"
|
||||
:data="childrenTableData"
|
||||
style="width: 100%;"
|
||||
:show-header="false"
|
||||
:size="'mini'"
|
||||
:height="'100%'">
|
||||
<el-table-column
|
||||
width="48">
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
v-for="(item, index) in tableTitlesOther"
|
||||
:key="index"
|
||||
show-overflow-tooltip
|
||||
:min-width="item.width"
|
||||
:label="item.label"
|
||||
:prop="item.prop"
|
||||
#default="{row}">
|
||||
<span v-if="item.prop === 'nameColumn'">
|
||||
{{ nameColumn === 'domainCategoryName' ? row['categoryName'] :(nameColumn === 'domainReputationLevel'? row['reputationLevel']:(nameColumn==='appCategory'?row['appCategoryName']:appRisk(row['appRiskLevel'])))}}
|
||||
</span>
|
||||
<span v-else-if="item.prop === 'tableNameColumn'">
|
||||
{{ tableNameColumn === 'appName' ? row['appName'] : row['domain']}}
|
||||
</span>
|
||||
<span v-else-if="item.prop === 'bytes'">
|
||||
{{unitConvert(row[item.prop], unitTypes.byte).join(' ')}}
|
||||
</span>
|
||||
<span v-else-if="item.prop === 'packets' || item.prop === 'sessions'">
|
||||
{{unitConvert(row[item.prop], unitTypes.number).join(' ')}}
|
||||
</span>
|
||||
<span v-else>
|
||||
{{ row[item.prop] }}
|
||||
</span>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</div>
|
||||
</template>
|
||||
</el-table-column>
|
||||
<el-table-column
|
||||
v-for="(item, index) in tableTitles"
|
||||
:key="index"
|
||||
show-overflow-tooltip
|
||||
:min-width="item.width"
|
||||
:label="(tableNameColumn === 'appName'&& item.prop === 'tableNameColumn')? $t('overall.appName'):item.label"
|
||||
:prop="item.prop"
|
||||
#default="{row}">
|
||||
<span v-if="item.prop === 'nameColumn'">
|
||||
{{ nameColumn === 'domainCategoryName' ? row['categoryName'] :(nameColumn === 'domainReputationLevel'? row['reputationLevel']:(nameColumn==='appCategory'?row['appCategoryName']:appRisk(row['appRiskLevel'])))}}
|
||||
</span>
|
||||
<span v-else-if="item.prop === 'tableNameColumn'">
|
||||
{{ tableNameColumn === 'appName' ? row['appName'] : row['domain']}}
|
||||
</span>
|
||||
<span v-else-if="item.prop === 'bytes'">
|
||||
{{unitConvert(row[item.prop], unitTypes.byte).join(' ')}}
|
||||
</span>
|
||||
<span v-else-if="item.prop === 'packets' || item.prop === 'sessions'">
|
||||
{{unitConvert(row[item.prop], unitTypes.number).join(' ')}}
|
||||
</span>
|
||||
<span v-else>
|
||||
{{ row[item.prop] }}
|
||||
</span>
|
||||
</el-table-column>
|
||||
</el-table>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import { get } from '@/utils/http'
|
||||
import { replaceUrlPlaceholder } from '@/utils/tools'
|
||||
import { unitTypes, riskLevelMapping } from '@/utils/constants'
|
||||
|
||||
export default {
|
||||
name: 'PieTable',
|
||||
props: {
|
||||
tableData: Array,
|
||||
chartInfo: Object,
|
||||
order: String,
|
||||
timeFilter: Object
|
||||
},
|
||||
watch: {
|
||||
tableData: {
|
||||
deep: true,
|
||||
immediate: true,
|
||||
handler (n) {
|
||||
this.pieTableData = JSON.parse((JSON.stringify(n)))
|
||||
this.pieTableData.forEach(item => {
|
||||
item.children = []
|
||||
})
|
||||
}
|
||||
},
|
||||
chartInfo: {
|
||||
deep: true,
|
||||
immediate: true,
|
||||
handler (n) {
|
||||
if (n && n.params) {
|
||||
this.nameColumn = n.params.nameColumn
|
||||
this.tableNameColumn = n.params.tableNameColumn
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
appRisk () {
|
||||
return function (level) {
|
||||
const m = riskLevelMapping.find(mapping => {
|
||||
return mapping.value == level
|
||||
})
|
||||
return (m && m.name) || level
|
||||
}
|
||||
}
|
||||
},
|
||||
data () {
|
||||
return {
|
||||
nameColumn: '',
|
||||
tableNameColumn: '',
|
||||
pieTableData: [],
|
||||
childrenTableData: [],
|
||||
expandRowKeys: [],
|
||||
tableTitles: [
|
||||
{
|
||||
label: this.$t('overall.domain'),
|
||||
prop: 'tableNameColumn', // 'domain'
|
||||
width: '20%'
|
||||
},
|
||||
{
|
||||
label: this.$t(this.chartInfo.params.tableTypeColumnLabel),
|
||||
prop: 'nameColumn',
|
||||
width: '22%'
|
||||
},
|
||||
{
|
||||
label: this.$t('overall.sessions'),
|
||||
prop: 'sessions',
|
||||
width: '18%'
|
||||
},
|
||||
{
|
||||
label: this.$t('overall.packets'),
|
||||
prop: 'packets',
|
||||
width: '18%'
|
||||
},
|
||||
{
|
||||
label: this.$t('overall.bytes'),
|
||||
prop: 'bytes',
|
||||
width: '18%'
|
||||
}
|
||||
],
|
||||
tableTitlesOther: [
|
||||
{
|
||||
label: this.$t('overall.serverIp'),
|
||||
prop: 'serverIp',
|
||||
width: '20%'
|
||||
},
|
||||
{
|
||||
label: this.$t('overall.reputation'),
|
||||
prop: 'nameColumn',
|
||||
width: '22%'
|
||||
},
|
||||
{
|
||||
label: this.$t('overall.sessions'),
|
||||
prop: 'sessions',
|
||||
width: '18%'
|
||||
},
|
||||
{
|
||||
label: this.$t('overall.packets'),
|
||||
prop: 'packets',
|
||||
width: '18%'
|
||||
},
|
||||
{
|
||||
label: this.$t('overall.bytes'),
|
||||
prop: 'bytes',
|
||||
width: '18%'
|
||||
}
|
||||
],
|
||||
loading: true
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
currentChange (row, expandedRows) {
|
||||
this.loading = true
|
||||
this.childrenTableData = []
|
||||
|
||||
if (this.tableNameColumn === 'appName') {
|
||||
if (this.expandRowKeys[0] && (row.appName === this.expandRowKeys[0])) {
|
||||
this.expandRowKeys = []
|
||||
} else {
|
||||
this.expandRowKeys = [row.appName]
|
||||
}
|
||||
} else {
|
||||
if (this.expandRowKeys[0] && (row.domain === this.expandRowKeys[0])) {
|
||||
this.expandRowKeys = []
|
||||
} else {
|
||||
this.expandRowKeys = [row.domain]
|
||||
}
|
||||
}
|
||||
|
||||
const url = this.chartInfo.params.urlChildrenTable
|
||||
let queryParams = {
|
||||
startTime: parseInt(this.timeFilter.startTime / 1000),
|
||||
endTime: parseInt(this.timeFilter.endTime / 1000),
|
||||
order: this.order,
|
||||
domain: row.domain,
|
||||
limit: 10
|
||||
}
|
||||
if (this.tableNameColumn === 'appName') {
|
||||
queryParams = {
|
||||
startTime: parseInt(this.timeFilter.startTime / 1000),
|
||||
endTime: parseInt(this.timeFilter.endTime / 1000),
|
||||
order: this.order,
|
||||
appName: row.appName,
|
||||
limit: 10
|
||||
}
|
||||
}
|
||||
setTimeout(() => {
|
||||
get(replaceUrlPlaceholder(url, queryParams)).then(response2 => {
|
||||
if (response2.code === 200) {
|
||||
this.childrenTableData = response2.data.result
|
||||
}
|
||||
}).finally(() => {
|
||||
this.loading = false
|
||||
})
|
||||
}, 500)
|
||||
},
|
||||
|
||||
getRowKey (row) {
|
||||
if (this.tableNameColumn === 'appName') {
|
||||
return row.appName
|
||||
} else {
|
||||
return row.domain
|
||||
}
|
||||
}
|
||||
},
|
||||
setup () {
|
||||
return {
|
||||
unitTypes,
|
||||
unitConvert
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -1,828 +0,0 @@
|
||||
/**
|
||||
* @author 陈劲松
|
||||
* @date 2021/6/16
|
||||
* @description chart option和一些工具
|
||||
*/
|
||||
import { format } from 'echarts'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import _ from 'lodash'
|
||||
export const chartColor = ['#5370C6', '#90CC74', '#FAC858', '#EE6666',
|
||||
'#73BFDE', '#3BA172', '#FC8452', '#9960B4',
|
||||
'#E97CCC', '#FEA69E', '#0F8AB2', '#57CBAC',
|
||||
'#5888BC', '#63B6AC', '#EDC6B2', '#D5746B']
|
||||
export const chartBarColor = ['#0F8AB2', '#57CBAC']
|
||||
export function getChartColor (index) {
|
||||
return chartColor[index % chartColor.length]
|
||||
}
|
||||
export function getCharBartColor (index) {
|
||||
return chartBarColor[index % chartBarColor.length]
|
||||
}
|
||||
const line = {
|
||||
tooltip: {
|
||||
appendToBody: true,
|
||||
trigger: 'axis',
|
||||
textStyle: {
|
||||
width: '20px',
|
||||
overflow: 'truncate'
|
||||
},
|
||||
formatter: axiosFormatter,
|
||||
show: true,
|
||||
className: 'nz-chart-tooltip',
|
||||
extraCssText: 'box-shadow: 0 0 3px rgba(0, 0, 0, 0.3);max-width: 300px !important'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'time'
|
||||
},
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
axisLabel: {
|
||||
formatter: function (value, index, a, b) {
|
||||
return unitConvert(value, unitTypes.number).join(' ')
|
||||
}
|
||||
},
|
||||
minInterval: 1
|
||||
},
|
||||
animation: false,
|
||||
grid: {
|
||||
left: 55,
|
||||
bottom: 30,
|
||||
top: 100,
|
||||
right: 25
|
||||
},
|
||||
color: chartColor,
|
||||
legend: {
|
||||
tooltip: {
|
||||
show: true,
|
||||
formatter: '{a}'
|
||||
},
|
||||
show: true,
|
||||
right: 23,
|
||||
top: 8,
|
||||
padding: 2,
|
||||
orient: 'horizontal',
|
||||
icon: 'circle',
|
||||
itemGap: 10,
|
||||
itemWidth: 10,
|
||||
textStyle: {
|
||||
padding: [0, 0, 0, 2],
|
||||
fontSize: 14
|
||||
},
|
||||
formatter: tooLongFormatter
|
||||
},
|
||||
axisLabel: {
|
||||
fontSize: 14
|
||||
},
|
||||
series: [
|
||||
{
|
||||
name: '',
|
||||
type: 'line',
|
||||
smooth: false,
|
||||
symbol: 'none',
|
||||
data: []
|
||||
}
|
||||
]
|
||||
}
|
||||
const lineWithStatistics = {
|
||||
tooltip: {
|
||||
appendToBody: true,
|
||||
trigger: 'axis',
|
||||
textStyle: {
|
||||
width: '20px',
|
||||
overflow: 'truncate'
|
||||
},
|
||||
formatter: axiosFormatter,
|
||||
className: 'nz-chart-tooltip',
|
||||
extraCssText: 'box-shadow: 0 0 3px rgba(0, 0, 0, 0.3);max-width: 300px !important'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'time'
|
||||
},
|
||||
animation: false,
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
axisLabel: {
|
||||
formatter: function (value, index) {
|
||||
return unitConvert(value, unitTypes.number).join(' ')
|
||||
}
|
||||
},
|
||||
minInterval: 1
|
||||
},
|
||||
color: chartColor,
|
||||
grid: {
|
||||
left: 55,
|
||||
bottom: 30,
|
||||
top: 20,
|
||||
right: 20
|
||||
},
|
||||
legend: {
|
||||
show: false
|
||||
},
|
||||
axisLabel: {
|
||||
fontSize: 14
|
||||
},
|
||||
series: [
|
||||
{
|
||||
name: '',
|
||||
type: 'line',
|
||||
smooth: false,
|
||||
symbol: 'none',
|
||||
data: []
|
||||
}
|
||||
]
|
||||
}
|
||||
const lineStack = {
|
||||
tooltip: {
|
||||
appendToBody: true,
|
||||
trigger: 'axis',
|
||||
textStyle: {
|
||||
width: '20px',
|
||||
overflow: 'truncate'
|
||||
},
|
||||
formatter: axiosFormatter,
|
||||
className: 'nz-chart-tooltip',
|
||||
extraCssText: 'box-shadow: 0 0 3px rgba(0, 0, 0, 0.3);max-width: 300px !important'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'time'
|
||||
},
|
||||
color: chartColor,
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
axisLabel: {
|
||||
formatter: function (value, index) {
|
||||
return unitConvert(value, unitTypes.number).join(' ')
|
||||
}
|
||||
},
|
||||
minInterval: 1
|
||||
},
|
||||
grid: {
|
||||
left: 55,
|
||||
bottom: 45,
|
||||
top: 10,
|
||||
right: 180
|
||||
},
|
||||
legend: {
|
||||
show: true,
|
||||
right: 30,
|
||||
top: 'middle',
|
||||
orient: 'vertical',
|
||||
icon: 'circle',
|
||||
itemGap: 20,
|
||||
itemWidth: 10,
|
||||
formatter: tooLongFormatter,
|
||||
textStyle: {
|
||||
padding: [0, 0, 0, 5],
|
||||
fontSize: 14
|
||||
}
|
||||
},
|
||||
axisLabel: {
|
||||
fontSize: 14
|
||||
},
|
||||
series: [
|
||||
{
|
||||
name: '',
|
||||
type: 'line',
|
||||
stack: 'value',
|
||||
areaStyle: {},
|
||||
symbol: 'none',
|
||||
data: []
|
||||
}
|
||||
]
|
||||
}
|
||||
const pieWithTable = {
|
||||
tooltip: {
|
||||
appendToBody: true
|
||||
},
|
||||
color: chartColor,
|
||||
animation: false,
|
||||
legend: {
|
||||
orient: 'vertical',
|
||||
type: 'plain',
|
||||
left: '60%',
|
||||
top: 'middle',
|
||||
icon: 'circle',
|
||||
itemWidth: 10, // 设置宽度
|
||||
itemHeight: 10, // 设置高度
|
||||
itemGap: 20,
|
||||
formatter: tooLongFormatter,
|
||||
tooltip: {
|
||||
show: true
|
||||
}
|
||||
},
|
||||
series: [
|
||||
{
|
||||
type: 'pie',
|
||||
selectedMode: 'single',
|
||||
radius: ['42%', '65%'],
|
||||
center: ['30%', '50%'],
|
||||
data: [],
|
||||
label: {
|
||||
formatter: '{d}%'
|
||||
},
|
||||
tooltip: {
|
||||
formatter: function (param, index, callback) {
|
||||
return `${param.name}: ${unitConvert(param.value, param.data.unitType).join(' ')}`
|
||||
}
|
||||
},
|
||||
emphasis: {
|
||||
itemStyle: {
|
||||
shadowBlur: 10,
|
||||
shadowOffsetX: 0,
|
||||
shadowColor: 'rgba(0, 0, 0, 0.5)'
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
const ipHostedDomain = {
|
||||
color: chartColor,
|
||||
animation: false,
|
||||
tooltip: {
|
||||
show: true
|
||||
},
|
||||
legend: {
|
||||
orient: 'vertical',
|
||||
type: 'plain',
|
||||
right: '8%',
|
||||
top: 'middle',
|
||||
icon: 'circle',
|
||||
itemWidth: 10, // 设置宽度
|
||||
itemHeight: 10, // 设置高度
|
||||
itemGap: 20,
|
||||
tooltip: {
|
||||
show: true
|
||||
}
|
||||
},
|
||||
series: [
|
||||
{
|
||||
type: 'pie',
|
||||
selectedMode: 'single',
|
||||
radius: ['42%', '65%'],
|
||||
center: ['36%', '50%'],
|
||||
data: [],
|
||||
label: {
|
||||
formatter: '{d}%'
|
||||
},
|
||||
tooltip: {
|
||||
formatter: function (param, index, callback) {
|
||||
return `${param.name}: ${unitConvert(param.value, param.data.unitType).join(' ')}`
|
||||
}
|
||||
},
|
||||
emphasis: {
|
||||
itemStyle: {
|
||||
shadowBlur: 10,
|
||||
shadowOffsetX: 0,
|
||||
shadowColor: 'rgba(0, 0, 0, 0.5)'
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
const singleValueLine = {
|
||||
tooltip: {
|
||||
show: true,
|
||||
enterable: true,
|
||||
showContent: true,
|
||||
appendToBody: true,
|
||||
trigger: 'axis',
|
||||
textStyle: {
|
||||
width: '20px',
|
||||
overflow: 'truncate'
|
||||
}
|
||||
},
|
||||
xAxis: {
|
||||
type: 'time',
|
||||
show: false
|
||||
},
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
show: false
|
||||
},
|
||||
animation: false,
|
||||
grid: {
|
||||
left: 0,
|
||||
bottom: 2,
|
||||
top: 5,
|
||||
right: 0
|
||||
},
|
||||
color: chartColor,
|
||||
legend: {
|
||||
show: false
|
||||
},
|
||||
series: [
|
||||
{
|
||||
type: 'line',
|
||||
legendHoverLink: false,
|
||||
itemStyle: {
|
||||
normal: {
|
||||
color: '#81C9FF',
|
||||
lineStyle: {
|
||||
width: 2
|
||||
}
|
||||
}
|
||||
},
|
||||
data: [],
|
||||
showSymbol: false,
|
||||
areaStyle: { color: '#C9EAFF' }
|
||||
}
|
||||
]
|
||||
}
|
||||
export const entityListLineOption = {
|
||||
tooltip: {
|
||||
appendToBody: true,
|
||||
trigger: 'axis',
|
||||
textStyle: {
|
||||
width: '20px',
|
||||
overflow: 'truncate'
|
||||
},
|
||||
formatter: axiosFormatter,
|
||||
show: true,
|
||||
className: 'nz-chart-tooltip',
|
||||
extraCssText: 'box-shadow: 0 0 3px rgba(0, 0, 0, 0.3);max-width: 300px !important'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'time',
|
||||
show: false
|
||||
},
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
show: false
|
||||
},
|
||||
animation: false,
|
||||
grid: {
|
||||
left: 0,
|
||||
bottom: 2,
|
||||
top: 5,
|
||||
right: 0
|
||||
},
|
||||
color: chartColor,
|
||||
legend: {
|
||||
show: false
|
||||
},
|
||||
series: [
|
||||
{
|
||||
type: 'line',
|
||||
legendHoverLink: false,
|
||||
itemStyle: {
|
||||
normal: {
|
||||
lineStyle: {
|
||||
width: 2
|
||||
}
|
||||
}
|
||||
},
|
||||
data: [],
|
||||
showSymbol: false
|
||||
}
|
||||
]
|
||||
}
|
||||
const relationShip = {
|
||||
grid: {
|
||||
left: 0,
|
||||
bottom: 50,
|
||||
top: 80,
|
||||
right: 0
|
||||
},
|
||||
series: [
|
||||
{
|
||||
type: 'graph',
|
||||
layout: 'force',
|
||||
symbolSize: 40,
|
||||
roam: true,
|
||||
force: {
|
||||
repulsion: 350
|
||||
},
|
||||
draggable: true,
|
||||
label: { show: true },
|
||||
edgeSymbol: ['none', 'arrow'],
|
||||
edgeSymbolSize: 7,
|
||||
data: [],
|
||||
links: []
|
||||
}
|
||||
]
|
||||
}
|
||||
const sankey = {
|
||||
tooltip: {
|
||||
trigger: 'item',
|
||||
triggerOn: 'mousemove'
|
||||
},
|
||||
series: [
|
||||
{
|
||||
type: 'sankey',
|
||||
data: [],
|
||||
links: [],
|
||||
right: '5%',
|
||||
top: 50,
|
||||
bottom: 100,
|
||||
levels: [
|
||||
{
|
||||
depth: 0,
|
||||
itemStyle: {
|
||||
color: '#47D49C'
|
||||
},
|
||||
lineStyle: {
|
||||
color: '#999'
|
||||
}
|
||||
}, {
|
||||
depth: 1,
|
||||
itemStyle: {
|
||||
color: '#A69BF5'
|
||||
},
|
||||
lineStyle: {
|
||||
color: '#999'
|
||||
}
|
||||
}, {
|
||||
depth: 2,
|
||||
itemStyle: {
|
||||
color: '#73A0FA'
|
||||
},
|
||||
lineStyle: {
|
||||
color: '#999'
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
const ipOpenPortBar = {
|
||||
xAxis: {
|
||||
type: 'category',
|
||||
axisTick: { show: false },
|
||||
axisLine: { show: false }
|
||||
},
|
||||
grid: {
|
||||
top: 30,
|
||||
left: 60,
|
||||
right: 50,
|
||||
bottom: 50
|
||||
},
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
show: false
|
||||
},
|
||||
series: [{
|
||||
barWidth: 38,
|
||||
data: [],
|
||||
type: 'bar',
|
||||
label: { show: true, position: 'top' },
|
||||
barCategoryGap: '10%'
|
||||
}]
|
||||
}
|
||||
const categoryBar = {
|
||||
tooltip: {
|
||||
appendToBody: true,
|
||||
trigger: 'axis',
|
||||
textStyle: {
|
||||
width: '20px',
|
||||
overflow: 'truncate'
|
||||
},
|
||||
formatter: categoryVerticalFormatter,
|
||||
show: true,
|
||||
className: 'nz-chart-tooltip',
|
||||
extraCssText: 'box-shadow: 0 0 3px rgba(0, 0, 0, 0.3);max-width: 300px !important'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'category',
|
||||
axisTick: { show: false },
|
||||
axisLine: { show: false }
|
||||
},
|
||||
grid: {
|
||||
top: 20,
|
||||
left: 10,
|
||||
right: 25,
|
||||
bottom: 20,
|
||||
containLabel: true
|
||||
},
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
axisTick: { show: false },
|
||||
axisLine: { show: false }
|
||||
},
|
||||
color: chartColor,
|
||||
series: [{
|
||||
barWidth: 15,
|
||||
data: [],
|
||||
type: 'bar',
|
||||
label: { show: false },
|
||||
barCategoryGap: '10%',
|
||||
itemStyle: {
|
||||
color: function (params) {
|
||||
return getCharBartColor([params.dataIndex])
|
||||
}
|
||||
}
|
||||
}]
|
||||
}
|
||||
|
||||
const timeBar = {
|
||||
tooltip: {
|
||||
appendToBody: true,
|
||||
trigger: 'axis',
|
||||
textStyle: {
|
||||
width: '20px',
|
||||
overflow: 'truncate'
|
||||
},
|
||||
formatter: timeVerticalFormatter,
|
||||
show: true,
|
||||
className: 'nz-chart-tooltip',
|
||||
extraCssText: 'box-shadow: 0 0 3px rgba(0, 0, 0, 0.3);max-width: 300px !important'
|
||||
},
|
||||
xAxis: {
|
||||
type: 'time',
|
||||
axisTick: { show: false },
|
||||
axisLine: { show: false },
|
||||
axisLabel: {
|
||||
interval: 0,
|
||||
// rotate: -40, //设置日期显示样式(倾斜度)
|
||||
formatter: function (value) { // 在这里写你需要的时间格式
|
||||
const t_date = new Date(value)
|
||||
return [t_date.getMonth() + 1, t_date.getDate()].join('/') + ' ' + [t_date.getHours(), t_date.getMinutes()].join(':')
|
||||
}
|
||||
}
|
||||
},
|
||||
grid: {
|
||||
top: 20,
|
||||
left: 25,
|
||||
right: 25,
|
||||
bottom: 20,
|
||||
containLabel: true
|
||||
},
|
||||
yAxis: {
|
||||
type: 'value',
|
||||
axisTick: { show: false },
|
||||
axisLine: { show: false },
|
||||
axisLabel: {
|
||||
formatter: function (value, index, a, b) {
|
||||
return unitConvert(value, unitTypes.number).join(' ')
|
||||
}
|
||||
},
|
||||
minInterval: 1
|
||||
},
|
||||
color: chartColor,
|
||||
series: [{
|
||||
barWidth: 15,
|
||||
data: [],
|
||||
type: 'bar',
|
||||
label: { show: false },
|
||||
barCategoryGap: '10%',
|
||||
itemStyle: {
|
||||
color: function (params) {
|
||||
return getCharBartColor([params.dataIndex])
|
||||
}
|
||||
}
|
||||
}]
|
||||
}
|
||||
const typeOptionMappings = [
|
||||
{ value: 11, option: line }, // 常规折线图
|
||||
{ value: 12, option: lineWithStatistics }, // 带统计表格的折线图
|
||||
{ value: 13, option: lineStack }, // 折线堆叠图
|
||||
{ value: 22, option: ipOpenPortBar }, // ip详情--开放端口的柱状图
|
||||
{ value: 23, option: timeBar }, // 矿机所属单位
|
||||
{ value: 24, option: categoryBar }, // 挖矿事件统计
|
||||
{ value: 31, option: pieWithTable }, // 常规折线图
|
||||
{ value: 33, option: ipHostedDomain }, // ip详情--托管域名
|
||||
{ value: 34, option: ipHostedDomain }, // app详情--相关域名
|
||||
{ value: 42, option: relationShip }, // 关系图
|
||||
{ value: 43, option: sankey }, // 桑基图
|
||||
{ value: 52, option: singleValueLine }
|
||||
]
|
||||
const typeCategory = {
|
||||
MAP: 'map',
|
||||
TABLE: 'table',
|
||||
ECHARTS: 'echarts',
|
||||
TITLE: 'title',
|
||||
SINGLE: 'singleValue',
|
||||
TABS: 'tabs'
|
||||
}
|
||||
export function getTypeCategory (type) {
|
||||
if (isMap(type)) {
|
||||
return typeCategory.MAP
|
||||
} else if (isEcharts(type)) {
|
||||
return typeCategory.ECHARTS
|
||||
} else if (isTable(type)) {
|
||||
return typeCategory.TABLE
|
||||
} else if (isSingleValue(type)) {
|
||||
return typeCategory.SINGLE
|
||||
} else if (isTitle(type)) {
|
||||
return typeCategory.TITLE
|
||||
} else if (isTabs(type)) {
|
||||
return typeCategory.TABS
|
||||
}
|
||||
}
|
||||
/* 柱状图:挖矿事件统计(time类型柱状图) */
|
||||
export function isEchartsTimeBar (type) {
|
||||
return type == 23
|
||||
}
|
||||
/* 柱状图:矿机所属单位(category类型柱状图) */
|
||||
export function isEchartsCategoryBar (type) {
|
||||
return type == 24
|
||||
}
|
||||
/* 饼图柱状图等 */
|
||||
export function isEcharts (type) {
|
||||
return type >= 11 && type <= 50
|
||||
}
|
||||
/* 地图 */
|
||||
export function isMap (type) {
|
||||
return type >= 1 && type <= 10
|
||||
}
|
||||
/* 连线地图 */
|
||||
export function isMapLine (type) {
|
||||
return type === 1
|
||||
}
|
||||
/* 色块地图 */
|
||||
export function isMapBlock (type) {
|
||||
return type === 2
|
||||
}
|
||||
/* 带统计的折线图 */
|
||||
export function isEchartsWithStatistics (type) {
|
||||
return type === 12
|
||||
}
|
||||
/* 关系图 */
|
||||
export function isRelationShip (type) {
|
||||
return type === 42
|
||||
}
|
||||
/* 桑基图 */
|
||||
export function isSankey (type) {
|
||||
return type === 43
|
||||
}
|
||||
/* 单值 */
|
||||
export function isSingleValue (type) {
|
||||
return type >= 51 && type <= 60
|
||||
}
|
||||
/* 带折线图的单值 */
|
||||
export function isSingleValueWithEcharts (type) {
|
||||
return type === 52
|
||||
}
|
||||
/* 带折线图的单值 */
|
||||
export function isSingleValueWithEchartsTemp (type) {
|
||||
return type === 55
|
||||
}
|
||||
/* 带Table的饼图 */
|
||||
export function isEchartsWithTable (type) {
|
||||
return type === 31
|
||||
}
|
||||
/* table */
|
||||
export function isTable (type) {
|
||||
return type >= 61 && type <= 70
|
||||
}
|
||||
/* table */
|
||||
export function isActiveIpTable (type) {
|
||||
return type == 63
|
||||
}
|
||||
/* title */
|
||||
export function isTitle (type) {
|
||||
return type === 93
|
||||
}
|
||||
/* tabs */
|
||||
export function isTabs (type) {
|
||||
return type === 91
|
||||
}
|
||||
/* IP实体基本信息 */
|
||||
export function isIpBasicInfo (type) {
|
||||
return type === 4
|
||||
}
|
||||
/* IP实体开放端口 */
|
||||
export function isIpOpenPort (type) {
|
||||
return type === 22
|
||||
}
|
||||
/* IP实体托管域名 */
|
||||
export function isIpHostedDomain (type) {
|
||||
return type === 33
|
||||
}
|
||||
/* APP实体相关域名 */
|
||||
export function isAppRelatedDomain (type) {
|
||||
return type === 34
|
||||
}
|
||||
/* APP实体基本信息 */
|
||||
export function isAppBasicInfo (type) {
|
||||
return type === 82
|
||||
}
|
||||
/* DOMAIN实体Whois */
|
||||
export function isDomainWhois (type) {
|
||||
return type === 83
|
||||
}
|
||||
/* DOMAIN实体DNS记录 */
|
||||
export function isDomainDnsRecord (type) {
|
||||
return type === 84
|
||||
}
|
||||
/* 近期挖矿事件 */
|
||||
export function isCryptocurrencyEventList (type) {
|
||||
return type === 85
|
||||
}
|
||||
/* 组 */
|
||||
export function isGroup (type) {
|
||||
return type === 94
|
||||
}
|
||||
/* 实体详情块 */
|
||||
export function isBlock (type) {
|
||||
return type === 95
|
||||
}
|
||||
export function getOption (type) {
|
||||
const mapping = typeOptionMappings.find(m => m.value === type)
|
||||
return mapping && mapping.option ? _.cloneDeep(mapping.option) : null
|
||||
}
|
||||
export const layoutConstant = {
|
||||
HEADER: 'header',
|
||||
FOOTER: 'footer'
|
||||
}
|
||||
export function getLayout (type) {
|
||||
const layout = []
|
||||
if (!isSingleValue(type) && !isTitle(type)) {
|
||||
layout.push(layoutConstant.HEADER)
|
||||
}
|
||||
if (type === 12 || type === 31) {
|
||||
layout.push(layoutConstant.FOOTER)
|
||||
}
|
||||
return layout
|
||||
}
|
||||
|
||||
function tooLongFormatter (name) {
|
||||
return format.truncateText(name, 110, '12')
|
||||
}
|
||||
function axiosFormatter (params) {
|
||||
let str = '<div>'
|
||||
params.forEach((item, i) => {
|
||||
const tData = item.data[0]
|
||||
if (i === 0) {
|
||||
str += '<div style="margin-bottom: 5px">'
|
||||
str += window.$dayJs.tz(tData).format('YYYY-MM-DD HH:mm:ss')
|
||||
str += '</div>'
|
||||
}
|
||||
str += '<div class="cn-chart-tooltip-box">'
|
||||
str += item.marker
|
||||
str += `<span class="cn-chart-tooltip-content">
|
||||
${item.seriesName}
|
||||
</span>`
|
||||
str += `<span class="cn-chart-tooltip-value">
|
||||
${unitConvert(item.data[1], item.data[2]).join(' ')}
|
||||
</span>`
|
||||
str += '</div>'
|
||||
})
|
||||
str += '</div>'
|
||||
return str
|
||||
}
|
||||
|
||||
export function timeVerticalFormatter (params) {
|
||||
let str = '<div>'
|
||||
params.forEach((item, i) => {
|
||||
const tData = item.data[0]
|
||||
if (i === 0) {
|
||||
str += '<div style="margin-bottom: 5px">'
|
||||
str += window.$dayJs.tz(tData).format('YYYY-MM-DD HH:mm:ss')
|
||||
str += '</div>'
|
||||
}
|
||||
str += '<div class="cn-chart-tooltip-box">'
|
||||
str += item.marker
|
||||
str += `<span class="cn-chart-tooltip-content">
|
||||
${item.seriesName}
|
||||
</span>`
|
||||
str += `<span class="cn-chart-tooltip-value">
|
||||
${unitConvert(item.data[1], item.data[2]).join(' ')}
|
||||
</span>`
|
||||
str += '</div>'
|
||||
})
|
||||
str += '</div>'
|
||||
return str
|
||||
}
|
||||
|
||||
export function timeHorizontalFormatter (params) {
|
||||
let str = '<div>'
|
||||
params.forEach((item, i) => {
|
||||
const tData = item.data[1]
|
||||
if (i === 0) {
|
||||
str += '<div style="margin-bottom: 5px">'
|
||||
str += window.$dayJs.tz(tData).format('YYYY-MM-DD HH:mm:ss')
|
||||
str += '</div>'
|
||||
}
|
||||
str += '<div class="cn-chart-tooltip-box">'
|
||||
str += item.marker
|
||||
str += `<span class="cn-chart-tooltip-content">
|
||||
${item.seriesName}
|
||||
</span>`
|
||||
str += `<span class="cn-chart-tooltip-value">
|
||||
${unitConvert(item.data[0], item.data[2]).join(' ')}
|
||||
</span>`
|
||||
str += '</div>'
|
||||
})
|
||||
str += '</div>'
|
||||
return str
|
||||
}
|
||||
export function categoryHorizontalFormatter (params) {
|
||||
let str = '<div>'
|
||||
params.forEach((item, i) => {
|
||||
str += '<div class="cn-chart-tooltip-box">'
|
||||
str += item.data[1] + ': ' + item.data[0]
|
||||
str += '</div>'
|
||||
})
|
||||
str += '</div>'
|
||||
return str
|
||||
}
|
||||
export function categoryVerticalFormatter (params) {
|
||||
let str = '<div>'
|
||||
params.forEach((item, i) => {
|
||||
str += '<div class="cn-chart-tooltip-box">'
|
||||
str += item.data[0] + ': ' + item.data[1]
|
||||
str += '</div>'
|
||||
})
|
||||
str += '</div>'
|
||||
return str
|
||||
}
|
||||
@@ -126,8 +126,8 @@
|
||||
import { get } from '@/utils/http'
|
||||
import { api } from '@/utils/api'
|
||||
import * as echarts from 'echarts'
|
||||
import { getChartColor, entityListLineOption } from '@/components/charts/chart-options'
|
||||
import { legendMapping } from '@/components/charts/chart-table-title'
|
||||
import { getChartColor, entityListLineOption } from '@/views/charts/charts/chart-options'
|
||||
import { legendMapping } from '@/views/charts/charts/chart-table-title'
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
|
||||
|
||||
@@ -10,6 +10,10 @@ const routes = [
|
||||
path: '/entityDetail',
|
||||
component: () => import('@/views/entityExplorer/EntityDetail')
|
||||
},
|
||||
{
|
||||
path: '/detections',
|
||||
component: () => import('@/views/detections/Index')
|
||||
},
|
||||
{
|
||||
path: '/',
|
||||
component: () => import('@/components/layout/Home'),
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,358 +0,0 @@
|
||||
<template>
|
||||
<div class="cn-chart">
|
||||
<loading :loading="loading && !isTabs && !isBlock && !isGroup"></loading>
|
||||
<chart-no-data v-if="isNoData"></chart-no-data>
|
||||
<template v-else>
|
||||
|
||||
<chart-tabs
|
||||
v-if="isTabs"
|
||||
:chart-info="chartInfo"
|
||||
:query-params="queryParams"
|
||||
:entity="entity"
|
||||
></chart-tabs>
|
||||
|
||||
<chart-map
|
||||
v-else-if="isMap && !isIpBasicInfo"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
:entity="entity"
|
||||
@showLoading="showLoading"
|
||||
></chart-map>
|
||||
|
||||
<chart-single-value
|
||||
v-else-if="isSingleValue"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
@showLoading="showLoading"
|
||||
></chart-single-value>
|
||||
|
||||
<chart-block
|
||||
v-else-if="isBlock"
|
||||
ref="chart"
|
||||
:timeFilter="queryParams"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:entity="entity"
|
||||
></chart-block>
|
||||
|
||||
<chart-group
|
||||
v-else-if="isGroup"
|
||||
:timeFilter="queryParams"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:entity="entity"
|
||||
></chart-group>
|
||||
|
||||
<ip-basic-info
|
||||
v-else-if="isIpBasicInfo"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:entity="entity"
|
||||
></ip-basic-info>
|
||||
|
||||
<chart-time-bar
|
||||
v-else-if="isEchartsTimeBar"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:result-type="resultType"
|
||||
:query-params="queryParams"
|
||||
@showLoading="showLoading"
|
||||
></chart-time-bar>
|
||||
|
||||
<chart-category-bar
|
||||
v-else-if="isEchartsCategoryBar"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:result-type="resultType"
|
||||
:query-params="queryParams"
|
||||
@showLoading="showLoading"
|
||||
></chart-category-bar>
|
||||
|
||||
<chart-ip-open-port-bar
|
||||
v-else-if="isIpOpenPortBar"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:result-type="resultType"
|
||||
:query-params="queryParams"
|
||||
@showLoading="showLoading"
|
||||
></chart-ip-open-port-bar>
|
||||
|
||||
<chart-table
|
||||
v-else-if="isTable && isCurrentTable"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:table="table"
|
||||
:query-params="queryParams"
|
||||
@showLoading="showLoading"
|
||||
></chart-table>
|
||||
|
||||
<chart-active-ip-table
|
||||
v-else-if="isActiveIpTable"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:table="table"
|
||||
:query-params="queryParams"
|
||||
></chart-active-ip-table>
|
||||
|
||||
<chart-app-basic-info
|
||||
v-else-if="isAppBasicInfo"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
></chart-app-basic-info>
|
||||
|
||||
<chart-domain-whois
|
||||
v-else-if="isDomainWhois"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
></chart-domain-whois>
|
||||
|
||||
<chart-domain-dns-record
|
||||
v-else-if="isDomainDnsRecord"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
></chart-domain-dns-record>
|
||||
|
||||
<chart-cryptocurrency-event-list
|
||||
v-else-if="isCryptocurrencyEventList"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
></chart-cryptocurrency-event-list>
|
||||
|
||||
<chart-relation-ship
|
||||
v-else-if="isRelationShip"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
></chart-relation-ship>
|
||||
|
||||
<chart-san-key
|
||||
v-else-if="isSankey"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
:entity="entity"
|
||||
></chart-san-key>
|
||||
|
||||
<chart-echart
|
||||
v-else-if="isEchartsLine || isEchartsPie"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:result-type="resultType"
|
||||
@showLoading="showLoading"
|
||||
></chart-echart>
|
||||
|
||||
<chart-echart-with-statistics
|
||||
v-else-if="isEchartsWithStatistics"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:result-type="resultType"
|
||||
@showLoading="showLoading"
|
||||
></chart-echart-with-statistics>
|
||||
|
||||
<chart-echart-with-table
|
||||
v-else-if="isEchartsWithTable"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
:query-params="queryParams"
|
||||
:result-type="resultType"
|
||||
:order-pie-table="orderPieTable"
|
||||
@showLoading="showLoading"
|
||||
></chart-echart-with-table>
|
||||
|
||||
<chart-echart-ip-hosted-domain
|
||||
v-else-if="isIpHostedDomain"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
@showLoading="showLoading"
|
||||
:entity="entity"
|
||||
></chart-echart-ip-hosted-domain>
|
||||
|
||||
<chart-echart-app-relate-domain
|
||||
v-else-if="isAppRelatedDomain"
|
||||
:chart-info="chartInfo"
|
||||
:chart-data="chartData"
|
||||
@showLoading="showLoading"
|
||||
:entity="entity"
|
||||
></chart-echart-app-relate-domain>
|
||||
|
||||
</template>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import Loading from '@/components/common/Loading'
|
||||
import ChartNoData from '@/views/charts/charts/ChartNoData'
|
||||
import ChartTabs from '@/views/charts/charts/ChartTabs'
|
||||
import ChartMap from '@/views/charts/charts/ChartMap'
|
||||
import ChartSingleValue from '@/views/charts/charts/ChartSingleValue'
|
||||
import ChartBlock from '@/views/charts/charts/ChartBlock'
|
||||
import ChartGroup from '@/views/charts/charts/ChartGroup'
|
||||
import IpBasicInfo from '@/views/charts/charts/IpBasicInfo'
|
||||
import ChartEchart from '@/views/charts/charts/ChartEchart'
|
||||
import ChartEchartWithStatistics from '@/views/charts/charts/ChartEchartWithStatistics'
|
||||
import ChartEchartWithTable from '@/views/charts/charts/ChartEchartWithTable'
|
||||
import ChartEchartIpHostedDomain from '@/views/charts/charts/ChartEchartIpHostedDomain'
|
||||
import ChartEchartAppRelateDomain from '@/views/charts/charts/ChartEchartAppRelateDomain'
|
||||
import ChartActiveIpTable from '@/views/charts/charts/ChartActiveIpTable'
|
||||
import ChartTimeBar from './charts/ChartTimeBar'
|
||||
import ChartCategoryBar from './charts/ChartCategoryBar'
|
||||
import ChartIpOpenPortBar from './charts/ChartIpOpenPortBar'
|
||||
import ChartTable from './charts/ChartTable'
|
||||
import ChartAppBasicInfo from '@/views/charts/charts/ChartAppBasicInfo'
|
||||
import ChartDomainWhois from '@/views/charts/charts/ChartDomainWhois'
|
||||
import ChartDomainDnsRecord from '@/views/charts/charts/ChartDomainDnsRecord'
|
||||
import ChartCryptocurrencyEventList from '@/views/charts/charts/ChartCryptocurrencyEventList'
|
||||
import ChartRelationShip from '@/views/charts/charts/ChartRelationShip'
|
||||
import ChartSanKey from '@/views/charts/charts/ChartSanKey'
|
||||
import {
|
||||
isEcharts,
|
||||
isEchartsLine,
|
||||
isSingleValue,
|
||||
isTable,
|
||||
isCurrentTable,
|
||||
isActiveIpTable,
|
||||
isTitle,
|
||||
isMap,
|
||||
getOption,
|
||||
isEchartsPie,
|
||||
isEchartsWithTable,
|
||||
isEchartsWithStatistics,
|
||||
isEchartsTimeBar,
|
||||
isEchartsCategoryBar,
|
||||
isIpOpenPortBar,
|
||||
isMapLine,
|
||||
isMapBlock,
|
||||
isSingleValueWithEcharts,
|
||||
isSingleValueWithEchartsTemp,
|
||||
isRelationShip,
|
||||
isTabs,
|
||||
isGroup,
|
||||
isSankey,
|
||||
isIpBasicInfo,
|
||||
isIpOpenPort,
|
||||
isIpHostedDomain,
|
||||
isDomainWhois,
|
||||
isDomainDnsRecord,
|
||||
isCryptocurrencyEventList,
|
||||
isAppBasicInfo,
|
||||
isAppRelatedDomain,
|
||||
isBlock
|
||||
} from './charts/tools'
|
||||
import _ from 'lodash'
|
||||
|
||||
export default {
|
||||
name: 'chart',
|
||||
components: {
|
||||
ChartSanKey,
|
||||
ChartCryptocurrencyEventList,
|
||||
ChartDomainDnsRecord,
|
||||
ChartDomainWhois,
|
||||
ChartAppBasicInfo,
|
||||
ChartActiveIpTable,
|
||||
ChartTable,
|
||||
IpBasicInfo,
|
||||
ChartSingleValue,
|
||||
Loading,
|
||||
ChartNoData,
|
||||
ChartTabs,
|
||||
ChartMap,
|
||||
ChartBlock,
|
||||
ChartTimeBar,
|
||||
ChartCategoryBar,
|
||||
ChartIpOpenPortBar,
|
||||
ChartRelationShip,
|
||||
ChartGroup,
|
||||
ChartEchartWithStatistics,
|
||||
ChartEchart,
|
||||
ChartEchartWithTable,
|
||||
ChartEchartIpHostedDomain,
|
||||
ChartEchartAppRelateDomain
|
||||
},
|
||||
props: {
|
||||
chartInfo: Object,
|
||||
chartData: [Object, Array, String], // 数据在父组件查询后传入,本组件内不查询,只根据接传递的数据来渲染
|
||||
resultType: Object, // 返回数据的类型
|
||||
queryParams: Object, // 接口请求参数
|
||||
customChartOption: Object, // 需要自定义echarts的option时传入,非必须;传入该值时仍需传对应格式的chartData
|
||||
isFullscreen: Boolean,
|
||||
loading: Boolean,
|
||||
panelLock: Boolean,
|
||||
entity: Object,
|
||||
isError: Boolean,
|
||||
table: Object,
|
||||
orderPieTable: Object
|
||||
},
|
||||
computed: {
|
||||
isNoData () {
|
||||
return !this.loading && (_.isEmpty(this.chartData) || this.isError) && !this.isSingleValue && !this.isTabs && !this.isDomainDnsRecord && !this.isCryptocurrencyEventList && !this.isActiveIpTable && !this.isMap
|
||||
},
|
||||
chartOption () {
|
||||
if (this.customChartOption) {
|
||||
return _.cloneDeep(this.customChartOption)
|
||||
} else {
|
||||
return getOption(this.chartInfo.type)
|
||||
}
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
resize () {
|
||||
this.$refs['chart' + this.chartInfo.id] && this.$refs['chart' + this.chartInfo.id].resize()
|
||||
},
|
||||
showLoading (show) {
|
||||
this.$emit('showLoading', show)
|
||||
},
|
||||
initEchartsWithTable () {
|
||||
this.$refs['chart' + this.chartInfo.id] && this.$refs['chart' + this.chartInfo.id].initEchartsWithTable(`chart${this.chartInfo.id}`)
|
||||
}
|
||||
|
||||
},
|
||||
watch: {
|
||||
chartData: {
|
||||
deep: true,
|
||||
handler (n) {
|
||||
}
|
||||
}
|
||||
},
|
||||
setup (props) {
|
||||
return {
|
||||
isEcharts: isEcharts(props.chartInfo.type),
|
||||
isEchartsLine: isEchartsLine(props.chartInfo.type),
|
||||
isEchartsTimeBar: isEchartsTimeBar(props.chartInfo.type),
|
||||
isEchartsCategoryBar: isEchartsCategoryBar(props.chartInfo.type),
|
||||
isIpOpenPortBar: isIpOpenPortBar(props.chartInfo.type),
|
||||
isEchartsPie: isEchartsPie(props.chartInfo.type),
|
||||
isEchartsWithTable: isEchartsWithTable(props.chartInfo.type),
|
||||
isEchartsWithStatistics: isEchartsWithStatistics(props.chartInfo.type),
|
||||
isSingleValue: isSingleValue(props.chartInfo.type),
|
||||
isSingleValueWithEcharts: isSingleValueWithEcharts(props.chartInfo.type),
|
||||
isSingleValueWithEchartsTemp: isSingleValueWithEchartsTemp(props.chartInfo.type),
|
||||
isRelationShip: isRelationShip(props.chartInfo.type),
|
||||
isTable: isTable(props.chartInfo.type),
|
||||
isCurrentTable: isCurrentTable(props.chartInfo.type),
|
||||
isActiveIpTable: isActiveIpTable(props.chartInfo.type),
|
||||
isMap: isMap(props.chartInfo.type),
|
||||
isTitle: isTitle(props.chartInfo.type),
|
||||
isMapLine: isMapLine(props.chartInfo.type),
|
||||
isMapBlock: isMapBlock(props.chartInfo.type),
|
||||
isTabs: isTabs(props.chartInfo.type),
|
||||
isGroup: isGroup(props.chartInfo.type),
|
||||
isBlock: isBlock(props.chartInfo.type),
|
||||
isSankey: isSankey(props.chartInfo.type),
|
||||
isIpBasicInfo: isIpBasicInfo(props.chartInfo.type),
|
||||
isIpHostedDomain: isIpHostedDomain(props.chartInfo.type),
|
||||
isIpOpenPort: isIpOpenPort(props.chartInfo.type),
|
||||
isDomainWhois: isDomainWhois(props.chartInfo.type),
|
||||
isDomainDnsRecord: isDomainDnsRecord(props.chartInfo.type),
|
||||
isCryptocurrencyEventList: isCryptocurrencyEventList(props.chartInfo.type),
|
||||
isAppBasicInfo: isAppBasicInfo(props.chartInfo.type),
|
||||
isAppRelatedDomain: isAppRelatedDomain(props.chartInfo.type)
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -115,7 +115,7 @@
|
||||
|
||||
<script>
|
||||
import { isTitle, isTabs, isBlock, isTable, isActiveIpTable, isCurrentTable, isGroup, isEchartsWithTable } from './charts/tools'
|
||||
import ChartError from '@/components/charts/ChartError'
|
||||
import ChartError from '@/views/charts/ChartError'
|
||||
import { getNowTime } from '@/utils/date-util'
|
||||
import { ref } from 'vue'
|
||||
import { chartTableTopOptions, chartActiveIpTableOrderOptions, chartPieTableTopOptions } from '@/utils/constants'
|
||||
|
||||
@@ -44,7 +44,7 @@
|
||||
|
||||
<script>
|
||||
import ChartHeader from './ChartHeader'
|
||||
import Chart from '@/views/charts/Chart2'
|
||||
import Chart from '@/views/charts/Chart'
|
||||
import testData from './charts/testData'
|
||||
import {
|
||||
isEcharts,
|
||||
@@ -75,7 +75,7 @@ import {
|
||||
isAppRelatedDomain,
|
||||
isBlock
|
||||
} from './charts/tools'
|
||||
import { tableTitleMapping, legendMapping } from '@/components/charts/chart-table-title'
|
||||
import { tableTitleMapping, legendMapping } from '@/views/charts/charts/chart-table-title'
|
||||
import { replaceUrlPlaceholder } from '@/utils/tools'
|
||||
import { getNowTime, getSecond } from '@/utils/date-util'
|
||||
import { chartPieTableTopOptions, chartTableDefaultPageSize, chartTableTopOptions } from '@/utils/constants'
|
||||
|
||||
@@ -7,7 +7,7 @@ import unitConvert from '@/utils/unit-convert'
|
||||
import * as echarts from 'echarts'
|
||||
import { lineToSpace } from '@/utils/tools'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import { legendMapping } from '@/components/charts/chart-table-title'
|
||||
import { legendMapping } from '@/views/charts/charts/chart-table-title'
|
||||
import {
|
||||
categoryBar
|
||||
} from '@/views/charts/charts/options/bar'
|
||||
|
||||
@@ -9,7 +9,7 @@ import { lineToSpace } from '@/utils/tools'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import chartEchartMixin from './chart-echart-mixin'
|
||||
import { getOption, isEchartsPie } from './tools'
|
||||
import { legendMapping } from '@/components/charts/chart-table-title'
|
||||
import { legendMapping } from '@/views/charts/charts/chart-table-title'
|
||||
|
||||
export default {
|
||||
name: 'ChartEchart',
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
|
||||
<script>
|
||||
import * as echarts from 'echarts'
|
||||
import StatisticsLegend from '@/components/charts/StatisticsLegend'
|
||||
import StatisticsLegend from '@/views/charts/charts/StatisticsLegend'
|
||||
import {
|
||||
lineWithStatistics
|
||||
} from '@/views/charts/charts/options/line'
|
||||
|
||||
@@ -36,7 +36,7 @@
|
||||
<script>
|
||||
import lodash from 'lodash'
|
||||
import { ipOpenPortBar } from '@/views/charts/charts/options/bar'
|
||||
import { getChartColor } from '@/components/charts/chart-options'
|
||||
import { getChartColor } from '@/views/charts/charts/chart-options'
|
||||
import * as echarts from 'echarts'
|
||||
export default {
|
||||
name: 'ChartIpOpenPortBar',
|
||||
|
||||
@@ -67,7 +67,7 @@ import {
|
||||
import { get } from '@/utils/http'
|
||||
import { replaceUrlPlaceholder } from '@/utils/tools'
|
||||
import * as echarts from 'echarts'
|
||||
import { getOption, getChartColor } from '@/components/charts/chart-options'
|
||||
import { getOption, getChartColor } from '@/views/charts/charts/chart-options'
|
||||
export default {
|
||||
name: 'chartSingleValue',
|
||||
props: {
|
||||
|
||||
@@ -7,7 +7,7 @@ import unitConvert from '@/utils/unit-convert'
|
||||
import * as echarts from 'echarts'
|
||||
import { lineToSpace } from '@/utils/tools'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import { legendMapping } from '@/components/charts/chart-table-title'
|
||||
import { legendMapping } from '@/views/charts/charts/chart-table-title'
|
||||
import {
|
||||
timeBar
|
||||
} from '@/views/charts/charts/options/bar'
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { getChartColor } from '@/components/charts/chart-options'
|
||||
import { getChartColor } from '@/views/charts/charts/chart-options'
|
||||
import unitConvert, { valueToRangeValue } from '@/utils/unit-convert'
|
||||
export default {
|
||||
name: 'StatisticsLegend',
|
||||
13
src/views/detections/Index.vue
Normal file
13
src/views/detections/Index.vue
Normal file
@@ -0,0 +1,13 @@
|
||||
<template>
|
||||
|
||||
</template>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
name: 'Index'
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped>
|
||||
|
||||
</style>
|
||||
@@ -1,487 +0,0 @@
|
||||
<template>
|
||||
<div class="outer-box">
|
||||
<div class="cn-entities">
|
||||
<el-input
|
||||
v-model="searchContentTemp"
|
||||
style="width: 100%; grid-area: 1 / 1 / 1 / 3;"
|
||||
type="text"
|
||||
@keyup.enter="enter"
|
||||
>
|
||||
<template #prefix>
|
||||
<span style="padding-left: 4px"><i class="el-icon-search"></i></span>
|
||||
</template>
|
||||
</el-input>
|
||||
<!-- 筛选区域 -->
|
||||
<left-filter
|
||||
:top-filter-data="topFilterData"
|
||||
:bottom-filter-data="bottomFilterData"
|
||||
@select="select"
|
||||
@showMore="showMore"
|
||||
style="grid-area: 2 / 1 / 3 / 2;"
|
||||
></left-filter>
|
||||
<!-- 内容区域 -->
|
||||
<entity-list
|
||||
:list-data="listData"
|
||||
:from="from"
|
||||
:loading="loading"
|
||||
:page-obj="pageObjRight"
|
||||
@showDetail="entityDetail"
|
||||
@pageNo="pageNoRight"
|
||||
style="grid-area: 2 / 2 / 3 / 3;"
|
||||
></entity-list>
|
||||
</div>
|
||||
</div>
|
||||
<entity-detail
|
||||
v-model:show-detail="showDetail"
|
||||
top="5vh"
|
||||
:show-close="false"
|
||||
:entity="currentEntity"></entity-detail>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import { entityType, entityFilterType } from '@/utils/constants'
|
||||
import LeftFilter from '@/components/entities/LeftFilter'
|
||||
import EntityList from '@/components/entities/EntityList'
|
||||
import { getEntityFilter, getEntityList, getEntityCount } from '@/utils/api'
|
||||
import { doubleQuotationToSingle } from '@/utils/tools'
|
||||
import EntityDetail from '@/components/entities/EntityDetail'
|
||||
export default {
|
||||
name: 'EntityExplorer',
|
||||
data () {
|
||||
return {
|
||||
searchContentTemp: '', // 搜索框内的文本内容,按回车键后为searchContent赋值
|
||||
searchContent: '', // 查询语句
|
||||
searchParams: null, // 搜索参数,格式为[{ name: xxx, value: xxx }, ...]
|
||||
filterObj: {}, // 被选中的左侧过滤条件
|
||||
topFilterData: {}, // 左侧上方的过滤列表数据
|
||||
bottomFilterData: {}, // 左侧下方的过滤列表数据
|
||||
listData: [], // 右侧实体列表数据
|
||||
pageObjLeftTop: {
|
||||
pageNo: 1,
|
||||
pageSize: 10,
|
||||
total: 0
|
||||
},
|
||||
pageObjLeftBottom: {
|
||||
pageNo: 1,
|
||||
pageSize: 10,
|
||||
total: 0
|
||||
},
|
||||
pageObjRight: {
|
||||
pageNo: 1,
|
||||
pageSize: 20,
|
||||
total: 0
|
||||
},
|
||||
showDetail: false,
|
||||
currentEntity: {},
|
||||
loading: true
|
||||
}
|
||||
},
|
||||
components: {
|
||||
EntityDetail,
|
||||
LeftFilter,
|
||||
EntityList
|
||||
},
|
||||
methods: {
|
||||
enter () {
|
||||
if (!this.searchContentTemp) {
|
||||
this.reset()
|
||||
} else {
|
||||
this.searchContent = this.searchContentTemp
|
||||
}
|
||||
},
|
||||
async showMore (column) {
|
||||
let index = 0
|
||||
switch (column) {
|
||||
case entityFilterType.ip.country:
|
||||
case entityFilterType.domain.categoryGroup:
|
||||
case entityFilterType.app.appCategory: {
|
||||
this.pageObjLeftTop.pageNo++
|
||||
break
|
||||
}
|
||||
case entityFilterType.ip.asn:
|
||||
case entityFilterType.domain.reputationLevel:
|
||||
case entityFilterType.app.appRisk: {
|
||||
index = 1
|
||||
this.pageObjLeftBottom.pageNo++
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
const { topFilterData, bottomFilterData } = await this.queryFilterData({ column, q: doubleQuotationToSingle(this.searchContent), from: this.from })
|
||||
if (index === 1) {
|
||||
this.bottomFilterData = {
|
||||
...this.bottomFilterData,
|
||||
data: this.$_.concat(this.bottomFilterData.data, bottomFilterData.data),
|
||||
hasnotMore: bottomFilterData.length < 10
|
||||
}
|
||||
} else {
|
||||
this.topFilterData = {
|
||||
...this.topFilterData,
|
||||
data: this.$_.concat(this.topFilterData.data, topFilterData.data),
|
||||
hasnotMore: topFilterData.length < 10
|
||||
}
|
||||
}
|
||||
},
|
||||
async search () {
|
||||
const vm = this
|
||||
const params = { from: this.from, q: doubleQuotationToSingle(this.searchContent) }
|
||||
this.loading = true
|
||||
try {
|
||||
this.listData = (await getEntityList({ ...this.pageObjRight, ...params })).map(d => {
|
||||
return {
|
||||
...d,
|
||||
id: window.btoa(unescape(encodeURIComponent(d.ip || d.domainName || d.appName))),
|
||||
latestSent: null,
|
||||
latestReceived: null
|
||||
}
|
||||
})
|
||||
this.pageObjRight.total = await getEntityCount(params)
|
||||
const { topFilterData, bottomFilterData } = await this.queryFilterData(params)
|
||||
this.topFilterData = topFilterData
|
||||
this.bottomFilterData = bottomFilterData
|
||||
} finally {
|
||||
setTimeout(() => {
|
||||
vm.loading = false
|
||||
}, 250)
|
||||
}
|
||||
},
|
||||
/* 重置条件 */
|
||||
reset () {
|
||||
this.pageObjLeftTop = {
|
||||
pageNo: 1,
|
||||
pageSize: 10
|
||||
}
|
||||
this.pageObjLeftBottom = {
|
||||
pageNo: 1,
|
||||
pageSize: 10
|
||||
}
|
||||
this.pageObjRight = {
|
||||
pageNo: 1,
|
||||
pageSize: 20
|
||||
}
|
||||
this.searchParams = null
|
||||
this.searchParams = []
|
||||
},
|
||||
async queryFilterData (params) {
|
||||
let topFilterParams = { ...params, ...this.pageObjLeftTop }
|
||||
let bottomFilterParams = { ...params, ...this.pageObjLeftBottom }
|
||||
const keys = Object.keys(this.filterObj)
|
||||
if (!this.$_.isEmpty(keys)) {
|
||||
let hasTopColumn = false
|
||||
let hasBottomColumn = false
|
||||
keys.forEach(key => {
|
||||
switch (key) {
|
||||
case entityFilterType.ip.country:
|
||||
case entityFilterType.domain.categoryGroup:
|
||||
case entityFilterType.app.appCategory: {
|
||||
hasTopColumn = true
|
||||
topFilterParams = { ...topFilterParams, column: key }
|
||||
break
|
||||
}
|
||||
case entityFilterType.ip.asn:
|
||||
case entityFilterType.domain.reputationLevel:
|
||||
case entityFilterType.app.appRisk: {
|
||||
hasBottomColumn = true
|
||||
bottomFilterParams = { ...bottomFilterParams, column: key }
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
})
|
||||
if (!hasTopColumn) {
|
||||
topFilterParams = { ...topFilterParams, column: this.getDefaultTopColumn(this.from) }
|
||||
}
|
||||
if (!hasBottomColumn) {
|
||||
bottomFilterParams = { ...bottomFilterParams, column: this.getDefaultBottomColumn(this.from) }
|
||||
}
|
||||
} else {
|
||||
topFilterParams = { ...topFilterParams, column: this.getDefaultTopColumn(this.from) }
|
||||
bottomFilterParams = { ...bottomFilterParams, column: this.getDefaultBottomColumn(this.from) }
|
||||
}
|
||||
const topFilterListData = await getEntityFilter(topFilterParams) || []
|
||||
const bottomFilterListData = await getEntityFilter(bottomFilterParams) || []
|
||||
let topFilterData = { data: topFilterListData, hasnotMore: topFilterListData.length < 10, column: topFilterParams.column }
|
||||
let bottomFilterData = { data: bottomFilterListData, hasnotMore: bottomFilterListData.length < 10, column: bottomFilterParams.column }
|
||||
switch (this.from) {
|
||||
case 'ip': {
|
||||
topFilterData = { ...topFilterData, icon: 'cn-icon cn-icon-country', title: this.$t('entities.countryOrRegion') }
|
||||
bottomFilterData = { ...bottomFilterData, icon: 'cn-icon cn-icon-cloud', title: this.$t('entities.asn') }
|
||||
break
|
||||
}
|
||||
case 'domain': {
|
||||
topFilterData = { ...topFilterData, icon: 'cn-icon cn-icon-category', title: this.$t('entities.groupAndName') }
|
||||
bottomFilterData = { ...bottomFilterData, icon: 'cn-icon cn-icon-risk', title: this.$t('entities.creditLevel') }
|
||||
break
|
||||
}
|
||||
case 'app': {
|
||||
topFilterData = { ...topFilterData, icon: 'cn-icon cn-icon-category', title: this.$t('entities.categoryAndSub') }
|
||||
bottomFilterData = { ...bottomFilterData, icon: 'cn-icon cn-icon-risk', title: this.$t('entities.riskLevel') }
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
return { topFilterData, bottomFilterData }
|
||||
},
|
||||
getDefaultTopColumn (from) {
|
||||
let column
|
||||
switch (from) {
|
||||
case 'ip': {
|
||||
column = entityFilterType.ip.country
|
||||
break
|
||||
}
|
||||
case 'domain': {
|
||||
column = entityFilterType.domain.categoryGroup
|
||||
break
|
||||
}
|
||||
case 'app': {
|
||||
column = entityFilterType.app.appCategory
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
return column
|
||||
},
|
||||
getDefaultBottomColumn (from) {
|
||||
let column = ''
|
||||
switch (from) {
|
||||
case 'ip': {
|
||||
column = entityFilterType.ip.asn
|
||||
break
|
||||
}
|
||||
case 'domain': {
|
||||
column = entityFilterType.domain.reputationLevel
|
||||
break
|
||||
}
|
||||
case 'app': {
|
||||
column = entityFilterType.app.appRisk
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
return column
|
||||
},
|
||||
async select (data, node, index, column) {
|
||||
if (index === 0) { // 上部过滤
|
||||
if (node.level === 1) {
|
||||
const columns = { ...this.filterObj, [column]: data.name }
|
||||
// 清除二级条件
|
||||
delete columns[entityFilterType.ip.region]
|
||||
delete columns[entityFilterType.domain.categoryName]
|
||||
delete columns[entityFilterType.app.appSubcategory]
|
||||
this.filterObj = columns
|
||||
} else if (node.level === 2) {
|
||||
const columns = { ...this.filterObj, [column]: data.parentName }
|
||||
// 清除一级条件
|
||||
let childColumn
|
||||
switch (column) {
|
||||
case entityFilterType.ip.country: {
|
||||
childColumn = entityFilterType.ip.region
|
||||
break
|
||||
}
|
||||
case entityFilterType.domain.categoryGroup: {
|
||||
childColumn = entityFilterType.domain.categoryName
|
||||
break
|
||||
}
|
||||
case entityFilterType.app.appCategory: {
|
||||
childColumn = entityFilterType.app.appSubcategory
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
columns[childColumn] = data.name
|
||||
this.filterObj = columns
|
||||
}
|
||||
} else if (index === 1) { // 下部过滤
|
||||
this.filterObj[column] = data.name
|
||||
}
|
||||
},
|
||||
async loadLevel2FilterData (node, parentColumn) {
|
||||
if (parentColumn) {
|
||||
const where = {}
|
||||
where[parentColumn] = node.data.name
|
||||
let column
|
||||
switch (parentColumn) {
|
||||
case entityFilterType.ip.country: {
|
||||
column = entityFilterType.ip.region
|
||||
break
|
||||
}
|
||||
case entityFilterType.domain.categoryGroup: {
|
||||
column = entityFilterType.domain.categoryName
|
||||
break
|
||||
}
|
||||
case entityFilterType.app.appCategory: {
|
||||
column = entityFilterType.app.appSubcategory
|
||||
break
|
||||
}
|
||||
default: break
|
||||
}
|
||||
const params = {
|
||||
q: doubleQuotationToSingle(this.searchContent),
|
||||
from: this.from,
|
||||
pageNo: 1,
|
||||
where,
|
||||
column
|
||||
}
|
||||
const result = await getEntityFilter(params)
|
||||
return result.map(r => ({ ...r, leaf: true, parentName: node.data.name }))
|
||||
} else {
|
||||
return []
|
||||
}
|
||||
},
|
||||
pageNoRight (val) {
|
||||
this.pageObjRight.pageNo = val
|
||||
this.search()
|
||||
},
|
||||
entityDetail (entity, tabs) {
|
||||
this.typeName = `${this.from.toLowerCase()}EntityDetail`
|
||||
this.currentEntity = entity
|
||||
this.showDetail = true
|
||||
}
|
||||
},
|
||||
watch: {
|
||||
/* entity类型切换时,分页、搜索信息重置 */
|
||||
from (n) {
|
||||
this.reset()
|
||||
},
|
||||
/* 搜索框searchContent、左侧过滤条件filterObj互相联动
|
||||
* 监听filterObj改动,将改动同步给searchParams
|
||||
* 监听searchContent改动,将改动同步给searchParams
|
||||
* 监听searchParams,将改动同步给filterObj、searchContent之一,并重新请求接口,获取左侧过滤条件和右侧entity列表
|
||||
* */
|
||||
filterObj: {
|
||||
deep: true,
|
||||
handler (n) {
|
||||
if (n) {
|
||||
const searchParams = this.$_.cloneDeep(this.searchParams)
|
||||
let change = false
|
||||
Object.keys(n).forEach(key => {
|
||||
let containKey = false
|
||||
searchParams.forEach(item => {
|
||||
if (item.name === key) {
|
||||
containKey = true
|
||||
if (item.value !== n[key]) {
|
||||
change = true
|
||||
item.value !== n[key] && (item.value = n[key])
|
||||
}
|
||||
}
|
||||
})
|
||||
if (!containKey) {
|
||||
change = true
|
||||
const name = key
|
||||
const value = n[key]
|
||||
const param = { name, value }
|
||||
searchParams.push(param)
|
||||
}
|
||||
})
|
||||
if (change) {
|
||||
this.searchParams = searchParams
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
searchContent (n) {
|
||||
if (n) {
|
||||
const paramsArr = n.split(/\s[aA][nN][dD]\s/)
|
||||
const paramsObj = {}
|
||||
let change = false
|
||||
paramsArr.forEach(string => {
|
||||
const param = string.split('=')
|
||||
if (param.length > 1) {
|
||||
let value = param[1].trim()
|
||||
const valueArr = value.split('"')
|
||||
if (valueArr.length > 2) {
|
||||
value = valueArr[1].trim()
|
||||
}
|
||||
paramsObj[param[0].trim()] = value
|
||||
}
|
||||
})
|
||||
const searchParams = this.$_.cloneDeep(this.searchParams)
|
||||
const newSearchParams = []
|
||||
const keys = Object.keys(paramsObj)
|
||||
keys.forEach(key => {
|
||||
newSearchParams.push({ name: key, value: paramsObj[key] })
|
||||
let containKey = false
|
||||
searchParams.forEach(item => {
|
||||
if (item.name === key) {
|
||||
containKey = true
|
||||
if (item.value !== paramsObj[key]) {
|
||||
change = true
|
||||
item.value = paramsObj[key]
|
||||
}
|
||||
}
|
||||
})
|
||||
if (!containKey) {
|
||||
change = true
|
||||
searchParams.push({ name: key, value: paramsObj[key] })
|
||||
}
|
||||
})
|
||||
if (newSearchParams.length !== searchParams.length) {
|
||||
this.searchParams = newSearchParams
|
||||
} else if (change) {
|
||||
this.searchParams = searchParams
|
||||
}
|
||||
} else {
|
||||
this.reset()
|
||||
}
|
||||
this.searchContentTemp !== n && (this.searchContentTemp = n)
|
||||
},
|
||||
searchParams: {
|
||||
deep: true,
|
||||
handler (n) {
|
||||
if (n) {
|
||||
let fromInput = false // input内容改变导致的变化
|
||||
let fromFilter = false // 左侧filter过滤条件改变导致的变化
|
||||
const filterKeys = Object.keys(this.filterObj)
|
||||
if (n.length === 0) {
|
||||
this.searchContentTemp = ''
|
||||
this.searchContent = ''
|
||||
this.filterObj = {}
|
||||
} else if (filterKeys.length !== n.length) {
|
||||
fromInput = true
|
||||
} else {
|
||||
fromFilter = true
|
||||
}
|
||||
if (fromInput) { // 是input导致的改变,则同步给filter
|
||||
const filterObj = {}
|
||||
n.forEach(item => {
|
||||
filterObj[item.name] = item.value
|
||||
})
|
||||
this.filterObj = filterObj
|
||||
}
|
||||
if (fromFilter) { // 是filter导致的改变,则同步给input
|
||||
let searchContent = ''
|
||||
n.forEach(item => {
|
||||
if (searchContent) {
|
||||
searchContent += ' AND '
|
||||
}
|
||||
searchContent += `${item.name}="${item.value}"`
|
||||
})
|
||||
this.searchContent = searchContent
|
||||
}
|
||||
// 请求接口,获取左侧过滤条件和右侧entity列表
|
||||
this.search()
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
from () {
|
||||
return this.$store.getters.from
|
||||
}
|
||||
},
|
||||
|
||||
async mounted () {
|
||||
this.$store.commit('showEntityTypeSelector', true)
|
||||
this.searchParams = []
|
||||
},
|
||||
setup () {
|
||||
return {
|
||||
entityType // 所有entity类型,用于header下拉框选择
|
||||
}
|
||||
},
|
||||
beforeUnmount () {
|
||||
this.$store.commit('entityTypeChange', Object.keys(entityType)[0])
|
||||
this.$store.commit('showEntityTypeSelector', false)
|
||||
}
|
||||
}
|
||||
</script>
|
||||
@@ -133,14 +133,14 @@
|
||||
</div>
|
||||
</div>
|
||||
<div class="overview-map overview-map--app">
|
||||
<chart2
|
||||
<chart
|
||||
:chart-info="chart"
|
||||
:chart-data="chartData"
|
||||
:entity="entityCopy"
|
||||
:query-params="getQueryParams"
|
||||
:hide-header="true"
|
||||
@getCurrentTimeRange="getCurrentTimeRange"
|
||||
></chart2>
|
||||
></chart>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -149,7 +149,7 @@ import { api } from '@/utils/api'
|
||||
import entityDetailMixin from './entityDetailMixin'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import Chart2 from '@/views/charts/Chart2'
|
||||
import Chart from '@/views/charts/Chart'
|
||||
import _ from 'lodash'
|
||||
import ChartSingleValue from '@/views/charts/charts/ChartSingleValue'
|
||||
import { get } from '@/utils/http'
|
||||
@@ -158,7 +158,7 @@ export default {
|
||||
name: 'App',
|
||||
mixins: [entityDetailMixin],
|
||||
components: {
|
||||
Chart2,
|
||||
Chart,
|
||||
ChartSingleValue
|
||||
},
|
||||
data () {
|
||||
|
||||
@@ -127,7 +127,7 @@
|
||||
<div class="row__label">{{$t('entities.recentSecurity')}}</div>
|
||||
<div class="row__content">{{entityData.securityNum || '-'}}</div>
|
||||
</div>
|
||||
<div class="overview__row overview__row--small-font" v-for="security in entityData.securityList">
|
||||
<div class="overview__row overview__row--small-font" v-for="(security, i) in entityData.securityList" :key="i">
|
||||
<div class="row__label row__label--width160">{{security.startTime}}</div>
|
||||
<div class="row__content row__content--width200">
|
||||
<div class="alert-level-tag alert-level-tag--high">{{security.securitySeverity}}</div>
|
||||
@@ -141,14 +141,14 @@
|
||||
</div>
|
||||
</div>
|
||||
<div class="overview-map">
|
||||
<chart2
|
||||
<chart
|
||||
:chart-info="chart"
|
||||
:chart-data="chartData"
|
||||
:entity="entityCopy"
|
||||
:query-params="getQueryParams"
|
||||
:hide-header="true"
|
||||
@getCurrentTimeRange="getCurrentTimeRange"
|
||||
></chart2>
|
||||
></chart>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -158,14 +158,14 @@ import { api } from '@/utils/api'
|
||||
import entityDetailMixin from './entityDetailMixin'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import Chart2 from '@/views/charts/Chart2'
|
||||
import Chart from '@/views/charts/Chart'
|
||||
import _ from 'lodash'
|
||||
import { get } from '@/utils/http'
|
||||
export default {
|
||||
name: 'Domain',
|
||||
components: {
|
||||
ChartSingleValue,
|
||||
Chart2
|
||||
Chart
|
||||
},
|
||||
mixins: [entityDetailMixin],
|
||||
data () {
|
||||
|
||||
@@ -125,14 +125,14 @@
|
||||
</div>
|
||||
</div>
|
||||
<div class="overview-map overview-map--ip">
|
||||
<chart2
|
||||
<chart
|
||||
:chart-info="chart"
|
||||
:chart-data="chartData"
|
||||
:entity="entityCopy"
|
||||
:query-params="getQueryParams"
|
||||
:hide-header="true"
|
||||
@getCurrentTimeRange="getCurrentTimeRange"
|
||||
></chart2>
|
||||
></chart>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
@@ -142,7 +142,7 @@ import ChartSingleValue from '@/views/charts/charts/ChartSingleValue'
|
||||
import { api } from '@/utils/api'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
import Chart2 from '@/views/charts/Chart2'
|
||||
import Chart from '@/views/charts/Chart'
|
||||
import _ from 'lodash'
|
||||
import { get } from '@/utils/http'
|
||||
|
||||
@@ -150,7 +150,7 @@ export default {
|
||||
name: 'Ip',
|
||||
mixins: [entityDetailMixin],
|
||||
components: {
|
||||
Chart2,
|
||||
Chart,
|
||||
ChartSingleValue
|
||||
},
|
||||
data () {
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
import _ from 'lodash'
|
||||
import { get } from '@/utils/http'
|
||||
import * as echarts from 'echarts'
|
||||
import { entityListLineOption } from '@/components/charts/chart-options'
|
||||
import { entityListLineOption } from '@/views/charts/charts/chart-options'
|
||||
import { unitTypes } from '@/utils/constants'
|
||||
import unitConvert from '@/utils/unit-convert'
|
||||
|
||||
|
||||
@@ -2,7 +2,7 @@ import _ from 'lodash'
|
||||
import { get } from '@/utils/http'
|
||||
import { api } from '@/utils/api'
|
||||
import * as echarts from 'echarts'
|
||||
import { entityListLineOption } from '@/components/charts/chart-options'
|
||||
import { entityListLineOption } from '@/views/charts/charts/chart-options'
|
||||
import { riskLevelMapping, unitTypes } from '@/utils/constants'
|
||||
|
||||
export default {
|
||||
|
||||
Reference in New Issue
Block a user