index.tsx 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161
  1. import React, { useEffect, useMemo, useRef, useState } from 'react'
  2. import Helmet from 'react-helmet'
  3. import Container from 'components/Container'
  4. import { init, EChartOption, ECharts } from 'echarts'
  5. import styles from './index.less'
  6. import api from 'utils/api'
  7. import request from 'utils/request'
  8. const DEFAULT_COLORS = [
  9. '#5470c6',
  10. '#91cc75',
  11. '#fac858',
  12. '#ee6666',
  13. '#73c0de',
  14. '#3ba272',
  15. '#fc8452',
  16. '#9a60b4',
  17. '#ea7ccc'
  18. ]
  19. // tslint:disable-next-line:interface-name
  20. interface DataOverviewState {
  21. originDept: number, // 来源部门数量
  22. countCatalogue: number, // 近一个月目录增长数量
  23. originSystem: number, // 来源系统数量
  24. dataSource: number, // 数据资源数量
  25. industryData: Array<{ name: string, value: number }>, // 行业分类饼图
  26. originDeptData: Array<{ name: string, value: number }>, // 来源部门柱状图
  27. }
  28. export default function DataOverview() {
  29. const pieElementRef = useRef<HTMLDivElement>(null)
  30. const barElementRef = useRef<HTMLDivElement>(null)
  31. const pieRef = useRef<ECharts>(null)
  32. const barRef = useRef<ECharts>(null)
  33. const [overview, setOverview] = useState<DataOverviewState>(
  34. {
  35. originDept: 0,
  36. countCatalogue: 0,
  37. originSystem: 0,
  38. dataSource: 0,
  39. industryData: [],
  40. originDeptData: []
  41. })
  42. const getDataScreening = async() => {
  43. try {
  44. const data = await request(api.dataScreening, { method: 'get' })
  45. setOverview((data as unknown as DataOverviewState))
  46. } catch (e) {
  47. console.log(e)
  48. }
  49. }
  50. const pieOption = useMemo<EChartOption>(() => ({
  51. tooltip: {
  52. trigger: 'item'
  53. },
  54. color: DEFAULT_COLORS,
  55. legend: {
  56. orient: 'vertical',
  57. right: 10,
  58. top: 'middle'
  59. },
  60. series: [
  61. {
  62. type: 'pie',
  63. radius: '50%',
  64. data: overview.industryData,
  65. emphasis: {
  66. itemStyle: {
  67. shadowBlur: 10,
  68. shadowOffsetX: 0,
  69. shadowColor: 'rgba(0, 0, 0, 0.5)'
  70. }
  71. }
  72. }
  73. ]
  74. }), [overview.industryData])
  75. const barOption = useMemo<EChartOption>(() => ({
  76. tooltip: {},
  77. dataset: {
  78. dimensions: ['name', 'value'],
  79. source: overview.originDeptData
  80. },
  81. xAxis: {},
  82. yAxis: {
  83. type: 'category',
  84. data: overview.originDeptData.map((o) => o.name)
  85. },
  86. series: [{
  87. type: 'bar',
  88. data: overview.originDeptData.map((o, idx) => ({
  89. value: o.value, itemStyle: {
  90. color: DEFAULT_COLORS[idx]
  91. }
  92. }))
  93. }]
  94. }), [overview.originDeptData])
  95. useEffect(() => {
  96. getDataScreening()
  97. }, [])
  98. useEffect(() => {
  99. barRef.current = init(barElementRef.current)
  100. barRef.current.setOption(barOption)
  101. }, [barOption])
  102. useEffect(() => {
  103. pieRef.current = init(pieElementRef.current)
  104. pieRef.current.setOption(pieOption)
  105. }, [pieOption])
  106. return (
  107. <Container>
  108. <Helmet title='数据总览' />
  109. <div className={styles['overview-container']}>
  110. <div className={styles['card-list']}>
  111. {[
  112. {
  113. title: '数据资源数量',
  114. num: overview.dataSource
  115. },
  116. {
  117. title: '来源部门数量',
  118. num: overview.originDept
  119. },
  120. {
  121. title: '来源系统数量',
  122. num: overview.originSystem
  123. },
  124. {
  125. title: '近一月目录新增数量',
  126. num: overview.countCatalogue
  127. }
  128. ].map((item) => (
  129. <div className={styles.item} key={item.title}>
  130. <div className={styles.title}>{item.title}</div>
  131. <div>
  132. <span className={styles.num}>{item.num}</span> 个
  133. </div>
  134. </div>
  135. ))}
  136. </div>
  137. <div className={styles.charts}>
  138. <div>
  139. <div className={styles['chart-title']}>行业分类</div>
  140. <div className={styles['chart-desc']}>资源目录各行业资源数量</div>
  141. <div ref={pieElementRef} />
  142. </div>
  143. <div>
  144. <div className={styles['chart-title']}>数据资源来源部门</div>
  145. <div className={styles['chart-desc']}>数据资源来源部门TOP10</div>
  146. <div ref={barElementRef} />
  147. </div>
  148. </div>
  149. </div>
  150. </Container>
  151. )
  152. }