Commit 3ffe2050827482ba83a1c15afbf346275be86187
1 parent
95d36770
首页改造,完成cpu,内存,网络图
Showing
18 changed files
with
711 additions
and
758 deletions
src/main/java/com/genersoft/iot/vmp/common/SystemAllInfo.java
0 → 100644
| 1 | +package com.genersoft.iot.vmp.common; | |
| 2 | + | |
| 3 | +import java.util.List; | |
| 4 | + | |
| 5 | +public class SystemAllInfo { | |
| 6 | + | |
| 7 | + private List<Object> cpu; | |
| 8 | + private List<Object> mem; | |
| 9 | + private List<Object> net; | |
| 10 | + | |
| 11 | + public List<Object> getCpu() { | |
| 12 | + return cpu; | |
| 13 | + } | |
| 14 | + | |
| 15 | + public void setCpu(List<Object> cpu) { | |
| 16 | + this.cpu = cpu; | |
| 17 | + } | |
| 18 | + | |
| 19 | + public List<Object> getMem() { | |
| 20 | + return mem; | |
| 21 | + } | |
| 22 | + | |
| 23 | + public void setMem(List<Object> mem) { | |
| 24 | + this.mem = mem; | |
| 25 | + } | |
| 26 | + | |
| 27 | + public List<Object> getNet() { | |
| 28 | + return net; | |
| 29 | + } | |
| 30 | + | |
| 31 | + public void setNet(List<Object> net) { | |
| 32 | + this.net = net; | |
| 33 | + } | |
| 34 | +} | ... | ... |
src/main/java/com/genersoft/iot/vmp/conf/SystemInfoTimerTask.java
| ... | ... | @@ -22,14 +22,14 @@ public class SystemInfoTimerTask { |
| 22 | 22 | @Autowired |
| 23 | 23 | private IRedisCatchStorage redisCatchStorage; |
| 24 | 24 | |
| 25 | - @Scheduled(fixedRate = 1000) //每1秒执行一次 | |
| 25 | + @Scheduled(fixedRate = 2000) //每1秒执行一次 | |
| 26 | 26 | public void execute(){ |
| 27 | 27 | try { |
| 28 | 28 | double cpuInfo = SystemInfoUtils.getCpuInfo(); |
| 29 | 29 | redisCatchStorage.addCpuInfo(cpuInfo); |
| 30 | 30 | double memInfo = SystemInfoUtils.getMemInfo(); |
| 31 | 31 | redisCatchStorage.addMemInfo(memInfo); |
| 32 | - Map<String, String> networkInterfaces = SystemInfoUtils.getNetworkInterfaces(); | |
| 32 | + Map<String, Double> networkInterfaces = SystemInfoUtils.getNetworkInterfaces(); | |
| 33 | 33 | redisCatchStorage.addNetInfo(networkInterfaces); |
| 34 | 34 | } catch (InterruptedException e) { |
| 35 | 35 | logger.error("[获取系统信息失败] {}", e.getMessage()); | ... | ... |
src/main/java/com/genersoft/iot/vmp/storager/IRedisCatchStorage.java
| ... | ... | @@ -2,6 +2,7 @@ package com.genersoft.iot.vmp.storager; |
| 2 | 2 | |
| 3 | 3 | import com.alibaba.fastjson.JSONObject; |
| 4 | 4 | import com.genersoft.iot.vmp.common.StreamInfo; |
| 5 | +import com.genersoft.iot.vmp.common.SystemAllInfo; | |
| 5 | 6 | import com.genersoft.iot.vmp.gb28181.bean.*; |
| 6 | 7 | import com.genersoft.iot.vmp.media.zlm.dto.*; |
| 7 | 8 | import com.genersoft.iot.vmp.service.bean.GPSMsgInfo; |
| ... | ... | @@ -196,7 +197,7 @@ public interface IRedisCatchStorage { |
| 196 | 197 | |
| 197 | 198 | void addMemInfo(double memInfo); |
| 198 | 199 | |
| 199 | - void addNetInfo(Map<String, String> networkInterfaces); | |
| 200 | + void addNetInfo(Map<String, Double> networkInterfaces); | |
| 200 | 201 | |
| 201 | 202 | void sendMobilePositionMsg(JSONObject jsonObject); |
| 202 | 203 | |
| ... | ... | @@ -240,4 +241,7 @@ public interface IRedisCatchStorage { |
| 240 | 241 | List<SendRtpItem> querySendRTPServerByChnnelId(String channelId); |
| 241 | 242 | |
| 242 | 243 | List<SendRtpItem> querySendRTPServerByStream(String stream); |
| 244 | + | |
| 245 | + SystemAllInfo getSystemInfo(); | |
| 246 | + | |
| 243 | 247 | } | ... | ... |
src/main/java/com/genersoft/iot/vmp/storager/impl/RedisCatchStorageImpl.java
| ... | ... | @@ -3,6 +3,7 @@ package com.genersoft.iot.vmp.storager.impl; |
| 3 | 3 | import com.alibaba.fastjson.JSON; |
| 4 | 4 | import com.alibaba.fastjson.JSONObject; |
| 5 | 5 | import com.genersoft.iot.vmp.common.StreamInfo; |
| 6 | +import com.genersoft.iot.vmp.common.SystemAllInfo; | |
| 6 | 7 | import com.genersoft.iot.vmp.common.SystemInfoDto; |
| 7 | 8 | import com.genersoft.iot.vmp.common.VideoManagerConstants; |
| 8 | 9 | import com.genersoft.iot.vmp.conf.UserSetting; |
| ... | ... | @@ -694,12 +695,12 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { |
| 694 | 695 | @Override |
| 695 | 696 | public void addCpuInfo(double cpuInfo) { |
| 696 | 697 | String key = VideoManagerConstants.SYSTEM_INFO_CPU_PREFIX + userSetting.getServerId(); |
| 697 | - SystemInfoDto<Double> systemInfoDto = new SystemInfoDto<>(); | |
| 698 | - systemInfoDto.setTime(DateUtil.getNow()); | |
| 699 | - systemInfoDto.setData(cpuInfo); | |
| 700 | - RedisUtil.lSet(key, systemInfoDto); | |
| 698 | + Map<String, String> infoMap = new HashMap<>(); | |
| 699 | + infoMap.put("time", DateUtil.getNow()); | |
| 700 | + infoMap.put("data", cpuInfo + ""); | |
| 701 | + RedisUtil.lSet(key, infoMap); | |
| 701 | 702 | // 每秒一个,最多只存30个 |
| 702 | - if (RedisUtil.lGetListSize(key) > 30) { | |
| 703 | + if (RedisUtil.lGetListSize(key) >= 30) { | |
| 703 | 704 | for (int i = 0; i < RedisUtil.lGetListSize(key) - 30; i++) { |
| 704 | 705 | RedisUtil.lLeftPop(key); |
| 705 | 706 | } |
| ... | ... | @@ -709,12 +710,12 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { |
| 709 | 710 | @Override |
| 710 | 711 | public void addMemInfo(double memInfo) { |
| 711 | 712 | String key = VideoManagerConstants.SYSTEM_INFO_MEM_PREFIX + userSetting.getServerId(); |
| 712 | - SystemInfoDto<Double> systemInfoDto = new SystemInfoDto<>(); | |
| 713 | - systemInfoDto.setTime(DateUtil.getNow()); | |
| 714 | - systemInfoDto.setData(memInfo); | |
| 715 | - RedisUtil.lSet(key, systemInfoDto); | |
| 713 | + Map<String, String> infoMap = new HashMap<>(); | |
| 714 | + infoMap.put("time", DateUtil.getNow()); | |
| 715 | + infoMap.put("data", memInfo + ""); | |
| 716 | + RedisUtil.lSet(key, infoMap); | |
| 716 | 717 | // 每秒一个,最多只存30个 |
| 717 | - if (RedisUtil.lGetListSize(key) > 30) { | |
| 718 | + if (RedisUtil.lGetListSize(key) >= 30) { | |
| 718 | 719 | for (int i = 0; i < RedisUtil.lGetListSize(key) - 30; i++) { |
| 719 | 720 | RedisUtil.lLeftPop(key); |
| 720 | 721 | } |
| ... | ... | @@ -722,14 +723,16 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { |
| 722 | 723 | } |
| 723 | 724 | |
| 724 | 725 | @Override |
| 725 | - public void addNetInfo(Map<String, String> networkInterfaces) { | |
| 726 | + public void addNetInfo(Map<String, Double> networkInterfaces) { | |
| 726 | 727 | String key = VideoManagerConstants.SYSTEM_INFO_NET_PREFIX + userSetting.getServerId(); |
| 727 | - SystemInfoDto<Map<String, String>> systemInfoDto = new SystemInfoDto<>(); | |
| 728 | - systemInfoDto.setTime(DateUtil.getNow()); | |
| 729 | - systemInfoDto.setData(networkInterfaces); | |
| 730 | - RedisUtil.lSet(key, systemInfoDto); | |
| 728 | + Map<String, Object> infoMap = new HashMap<>(); | |
| 729 | + infoMap.put("time", DateUtil.getNow()); | |
| 730 | + for (String netKey : networkInterfaces.keySet()) { | |
| 731 | + infoMap.put(netKey, networkInterfaces.get(netKey)); | |
| 732 | + } | |
| 733 | + RedisUtil.lSet(key, infoMap); | |
| 731 | 734 | // 每秒一个,最多只存30个 |
| 732 | - if (RedisUtil.lGetListSize(key) > 30) { | |
| 735 | + if (RedisUtil.lGetListSize(key) >= 30) { | |
| 733 | 736 | for (int i = 0; i < RedisUtil.lGetListSize(key) - 30; i++) { |
| 734 | 737 | RedisUtil.lLeftPop(key); |
| 735 | 738 | } |
| ... | ... | @@ -737,6 +740,18 @@ public class RedisCatchStorageImpl implements IRedisCatchStorage { |
| 737 | 740 | } |
| 738 | 741 | |
| 739 | 742 | @Override |
| 743 | + public SystemAllInfo getSystemInfo() { | |
| 744 | + String cpuKey = VideoManagerConstants.SYSTEM_INFO_CPU_PREFIX + userSetting.getServerId(); | |
| 745 | + String memKey = VideoManagerConstants.SYSTEM_INFO_MEM_PREFIX + userSetting.getServerId(); | |
| 746 | + String netKey = VideoManagerConstants.SYSTEM_INFO_NET_PREFIX + userSetting.getServerId(); | |
| 747 | + SystemAllInfo systemAllInfo = new SystemAllInfo(); | |
| 748 | + systemAllInfo.setCpu(RedisUtil.lGet(cpuKey, 0, -1)); | |
| 749 | + systemAllInfo.setMem(RedisUtil.lGet(memKey, 0, -1)); | |
| 750 | + systemAllInfo.setNet(RedisUtil.lGet(netKey, 0, -1)); | |
| 751 | + return systemAllInfo; | |
| 752 | + } | |
| 753 | + | |
| 754 | + @Override | |
| 740 | 755 | public void sendMobilePositionMsg(JSONObject jsonObject) { |
| 741 | 756 | String key = VideoManagerConstants.VM_MSG_SUBSCRIBE_MOBILE_POSITION; |
| 742 | 757 | logger.info("[redis发送通知] 移动位置 {}: {}", key, jsonObject.toString()); | ... | ... |
src/main/java/com/genersoft/iot/vmp/utils/SystemInfoUtils.java
| ... | ... | @@ -8,6 +8,7 @@ import oshi.hardware.NetworkIF; |
| 8 | 8 | import oshi.software.os.OperatingSystem; |
| 9 | 9 | import oshi.util.FormatUtil; |
| 10 | 10 | |
| 11 | +import java.text.DecimalFormat; | |
| 11 | 12 | import java.util.HashMap; |
| 12 | 13 | import java.util.List; |
| 13 | 14 | import java.util.Map; |
| ... | ... | @@ -62,21 +63,32 @@ public class SystemInfoUtils { |
| 62 | 63 | * 获取网络上传和下载 |
| 63 | 64 | * @return |
| 64 | 65 | */ |
| 65 | - public static Map<String,String> getNetworkInterfaces() { | |
| 66 | + public static Map<String,Double> getNetworkInterfaces() { | |
| 66 | 67 | SystemInfo si = new SystemInfo(); |
| 67 | 68 | HardwareAbstractionLayer hal = si.getHardware(); |
| 68 | - List<NetworkIF> networkIFs = hal.getNetworkIFs(); | |
| 69 | - int i= networkIFs.size() -1; | |
| 70 | - NetworkIF net= networkIFs.get(i); | |
| 69 | + List<NetworkIF> beforeRecvNetworkIFs = hal.getNetworkIFs(); | |
| 70 | + NetworkIF beforeBet= beforeRecvNetworkIFs.get(beforeRecvNetworkIFs.size() - 1); | |
| 71 | + long beforeRecv = beforeBet.getBytesRecv(); | |
| 72 | + long beforeSend = beforeBet.getBytesSent(); | |
| 73 | + try { | |
| 74 | + Thread.sleep(1000); | |
| 75 | + } catch (InterruptedException e) { | |
| 76 | + throw new RuntimeException(e); | |
| 77 | + } | |
| 78 | + List<NetworkIF> afterNetworkIFs = hal.getNetworkIFs(); | |
| 79 | + NetworkIF afterNet = afterNetworkIFs.get(afterNetworkIFs.size() - 1); | |
| 71 | 80 | |
| 72 | - String in = FormatUtil.formatBytes(net.getBytesRecv()); | |
| 73 | - String out = FormatUtil.formatBytes(net.getBytesSent()); | |
| 74 | - HashMap<String, String> map = new HashMap<>(); | |
| 75 | - map.put("in",in); | |
| 76 | - map.put("out",out); | |
| 81 | + HashMap<String, Double> map = new HashMap<>(); | |
| 82 | + // 速度单位: Mbps | |
| 83 | + map.put("in",formatUnits(afterNet.getBytesRecv()-beforeRecv, 1048576L)); | |
| 84 | + map.put("out",formatUnits(afterNet.getBytesSent()-beforeSend, 1048576L)); | |
| 77 | 85 | return map; |
| 78 | 86 | } |
| 79 | 87 | |
| 88 | + public static double formatUnits(long value, long prefix) { | |
| 89 | + return (double)value / (double)prefix; | |
| 90 | + } | |
| 91 | + | |
| 80 | 92 | /** |
| 81 | 93 | * 获取进程数 |
| 82 | 94 | * @return | ... | ... |
src/main/java/com/genersoft/iot/vmp/vmanager/server/ServerController.java
| ... | ... | @@ -3,6 +3,7 @@ package com.genersoft.iot.vmp.vmanager.server; |
| 3 | 3 | import com.alibaba.fastjson.JSON; |
| 4 | 4 | import com.alibaba.fastjson.JSONObject; |
| 5 | 5 | import com.genersoft.iot.vmp.VManageBootstrap; |
| 6 | +import com.genersoft.iot.vmp.common.SystemAllInfo; | |
| 6 | 7 | import com.genersoft.iot.vmp.common.VersionPo; |
| 7 | 8 | import com.genersoft.iot.vmp.conf.SipConfig; |
| 8 | 9 | import com.genersoft.iot.vmp.conf.UserSetting; |
| ... | ... | @@ -12,6 +13,7 @@ import com.genersoft.iot.vmp.media.zlm.ZlmHttpHookSubscribe; |
| 12 | 13 | import com.genersoft.iot.vmp.media.zlm.dto.IHookSubscribe; |
| 13 | 14 | import com.genersoft.iot.vmp.media.zlm.dto.MediaServerItem; |
| 14 | 15 | import com.genersoft.iot.vmp.service.IMediaServerService; |
| 16 | +import com.genersoft.iot.vmp.storager.IRedisCatchStorage; | |
| 15 | 17 | import com.genersoft.iot.vmp.utils.SpringBeanFactory; |
| 16 | 18 | import com.genersoft.iot.vmp.vmanager.bean.ErrorCode; |
| 17 | 19 | import gov.nist.javax.sip.SipStackImpl; |
| ... | ... | @@ -60,6 +62,9 @@ public class ServerController { |
| 60 | 62 | @Autowired |
| 61 | 63 | private ThreadPoolTaskExecutor taskExecutor; |
| 62 | 64 | |
| 65 | + @Autowired | |
| 66 | + private IRedisCatchStorage redisCatchStorage; | |
| 67 | + | |
| 63 | 68 | |
| 64 | 69 | @GetMapping(value = "/media_server/list") |
| 65 | 70 | @ResponseBody |
| ... | ... | @@ -202,4 +207,12 @@ public class ServerController { |
| 202 | 207 | public List<IHookSubscribe> getHooks() { |
| 203 | 208 | return zlmHttpHookSubscribe.getAll(); |
| 204 | 209 | } |
| 210 | + | |
| 211 | + @GetMapping(value = "/system/info") | |
| 212 | + @ResponseBody | |
| 213 | + @Operation(summary = "获取系统信息") | |
| 214 | + public SystemAllInfo getSystemInfo() { | |
| 215 | + SystemAllInfo systemAllInfo = redisCatchStorage.getSystemInfo(); | |
| 216 | + return systemAllInfo; | |
| 217 | + } | |
| 205 | 218 | } | ... | ... |
src/main/java/com/genersoft/iot/vmp/web/gb28181/ApiDeviceController.java
| ... | ... | @@ -40,7 +40,7 @@ public class ApiDeviceController { |
| 40 | 40 | // private DeviceOffLineDetector offLineDetector; |
| 41 | 41 | |
| 42 | 42 | /** |
| 43 | - * 分页获取设备列表 TODO 现在直接返回,尚未实现分页 | |
| 43 | + * 分页获取设备列表 现在直接返回,尚未实现分页 | |
| 44 | 44 | * @param start |
| 45 | 45 | * @param limit |
| 46 | 46 | * @param q |
| ... | ... | @@ -130,11 +130,11 @@ public class ApiDeviceController { |
| 130 | 130 | deviceJOSNChannel.put("DeviceID", device.getDeviceId()); |
| 131 | 131 | deviceJOSNChannel.put("DeviceName", device.getName()); |
| 132 | 132 | deviceJOSNChannel.put("DeviceOnline", device.getOnline() == 1); |
| 133 | - deviceJOSNChannel.put("Channel", 0); // TODO 自定义序号 | |
| 133 | + deviceJOSNChannel.put("Channel", 0); // 自定义序号 | |
| 134 | 134 | deviceJOSNChannel.put("Name", deviceChannel.getName()); |
| 135 | 135 | deviceJOSNChannel.put("Custom", false); |
| 136 | 136 | deviceJOSNChannel.put("CustomName", ""); |
| 137 | - deviceJOSNChannel.put("SubCount", deviceChannel.getSubCount()); // TODO ? 子节点数, SubCount > 0 表示该通道为子目录 | |
| 137 | + deviceJOSNChannel.put("SubCount", deviceChannel.getSubCount()); // 子节点数, SubCount > 0 表示该通道为子目录 | |
| 138 | 138 | deviceJOSNChannel.put("SnapURL", ""); |
| 139 | 139 | deviceJOSNChannel.put("Manufacturer ", deviceChannel.getManufacture()); |
| 140 | 140 | deviceJOSNChannel.put("Model", deviceChannel.getModel()); | ... | ... |
src/main/java/com/genersoft/iot/vmp/web/gb28181/ApiStreamController.java
| ... | ... | @@ -57,12 +57,12 @@ public class ApiStreamController { |
| 57 | 57 | * @param serial 设备编号 |
| 58 | 58 | * @param channel 通道序号 默认值: 1 |
| 59 | 59 | * @param code 通道编号,通过 /api/v1/device/channellist 获取的 ChannelList.ID, 该参数和 channel 二选一传递即可 |
| 60 | - * @param cdn TODO 转推 CDN 地址, 形如: [rtmp|rtsp]://xxx, encodeURIComponent | |
| 61 | - * @param audio TODO 是否开启音频, 默认 开启 | |
| 60 | + * @param cdn 转推 CDN 地址, 形如: [rtmp|rtsp]://xxx, encodeURIComponent | |
| 61 | + * @param audio 是否开启音频, 默认 开启 | |
| 62 | 62 | * @param transport 流传输模式, 默认 UDP |
| 63 | - * @param checkchannelstatus TODO 是否检查通道状态, 默认 false, 表示 拉流前不检查通道状态是否在线 | |
| 64 | - * @param transportmode TODO 当 transport=TCP 时有效, 指示流传输主被动模式, 默认被动 | |
| 65 | - * @param timeout TODO 拉流超时(秒), | |
| 63 | + * @param checkchannelstatus 是否检查通道状态, 默认 false, 表示 拉流前不检查通道状态是否在线 | |
| 64 | + * @param transportmode 当 transport=TCP 时有效, 指示流传输主被动模式, 默认被动 | |
| 65 | + * @param timeout 拉流超时(秒), | |
| 66 | 66 | * @return |
| 67 | 67 | */ |
| 68 | 68 | @RequestMapping(value = "/start") | ... | ... |
web_src/package-lock.json
| ... | ... | @@ -18,6 +18,7 @@ |
| 18 | 18 | "ol": "^6.14.1", |
| 19 | 19 | "postcss-pxtorem": "^5.1.1", |
| 20 | 20 | "uuid": "^8.3.2", |
| 21 | + "v-charts": "^1.19.0", | |
| 21 | 22 | "vue": "^2.6.11", |
| 22 | 23 | "vue-clipboard2": "^0.3.1", |
| 23 | 24 | "vue-clipboards": "^1.3.0", |
| ... | ... | @@ -3938,12 +3939,31 @@ |
| 3938 | 3939 | }, |
| 3939 | 3940 | "node_modules/echarts": { |
| 3940 | 3941 | "version": "4.9.0", |
| 3941 | - "resolved": "https://registry.nlark.com/echarts/download/echarts-4.9.0.tgz?cache=0&sync_timestamp=1619495447964&other_urls=https%3A%2F%2Fregistry.nlark.com%2Fecharts%2Fdownload%2Fecharts-4.9.0.tgz", | |
| 3942 | - "integrity": "sha1-qbm6oD8Doqcx5jQMVb77V6nhNH0=", | |
| 3942 | + "resolved": "https://registry.npmmirror.com/echarts/-/echarts-4.9.0.tgz", | |
| 3943 | + "integrity": "sha512-+ugizgtJ+KmsJyyDPxaw2Br5FqzuBnyOWwcxPKO6y0gc5caYcfnEUIlNStx02necw8jmKmTafmpHhGo4XDtEIA==", | |
| 3943 | 3944 | "dependencies": { |
| 3944 | 3945 | "zrender": "4.3.2" |
| 3945 | 3946 | } |
| 3946 | 3947 | }, |
| 3948 | + "node_modules/echarts-amap": { | |
| 3949 | + "version": "1.0.0-rc.6", | |
| 3950 | + "resolved": "https://registry.npmmirror.com/echarts-amap/-/echarts-amap-1.0.0-rc.6.tgz", | |
| 3951 | + "integrity": "sha512-cYJCKoQdnkZXrGweYrveU1HruZd1c0KmsF1U8o3FtsvgR2jVL5ZUpGFjMmFtpolHOUFqxizk+s+QBLkYuOWL6Q==" | |
| 3952 | + }, | |
| 3953 | + "node_modules/echarts-liquidfill": { | |
| 3954 | + "version": "2.0.6", | |
| 3955 | + "resolved": "https://registry.npmmirror.com/echarts-liquidfill/-/echarts-liquidfill-2.0.6.tgz", | |
| 3956 | + "integrity": "sha512-p+AH0O9/BtwXMQQyhjJbMZo+GwRAgWG/DCyK5r27PQzpS0UWrgXu57MyEFc0A8Ub3sRuqEu08BuxwHICBkSWSQ==", | |
| 3957 | + "peerDependencies": { | |
| 3958 | + "echarts": "^4.8.0", | |
| 3959 | + "zrender": "^4.3.1" | |
| 3960 | + } | |
| 3961 | + }, | |
| 3962 | + "node_modules/echarts-wordcloud": { | |
| 3963 | + "version": "1.1.3", | |
| 3964 | + "resolved": "https://registry.npmmirror.com/echarts-wordcloud/-/echarts-wordcloud-1.1.3.tgz", | |
| 3965 | + "integrity": "sha512-Et8D5xEAoYkidmHun+hEH+2lF9dhCt6D0JJ390vlr2r/1zwhhZAbcL01CEvG93QcMcJpSvSPK8vRiGkTbMHRxg==" | |
| 3966 | + }, | |
| 3947 | 3967 | "node_modules/ee-first": { |
| 3948 | 3968 | "version": "1.1.1", |
| 3949 | 3969 | "resolved": "https://registry.npm.taobao.org/ee-first/download/ee-first-1.1.1.tgz", |
| ... | ... | @@ -7160,6 +7180,11 @@ |
| 7160 | 7180 | "node": ">=0.10.0" |
| 7161 | 7181 | } |
| 7162 | 7182 | }, |
| 7183 | + "node_modules/numerify": { | |
| 7184 | + "version": "1.2.9", | |
| 7185 | + "resolved": "https://registry.npmmirror.com/numerify/-/numerify-1.2.9.tgz", | |
| 7186 | + "integrity": "sha512-X4QzQiytV5ZN3TVLhzbtFzjTarUNnaa1pgNDFqt7u7Nqhxe7FvY2eYrGt4WYHlYXDqgtfC/n/a5nJ2y0LijV8w==" | |
| 7187 | + }, | |
| 7163 | 7188 | "node_modules/object-assign": { |
| 7164 | 7189 | "version": "4.1.1", |
| 7165 | 7190 | "resolved": "https://registry.npm.taobao.org/object-assign/download/object-assign-4.1.1.tgz", |
| ... | ... | @@ -13004,6 +13029,11 @@ |
| 13004 | 13029 | "integrity": "sha1-ihagXURWV6Oupe7MWxKk+lN5dyw=", |
| 13005 | 13030 | "dev": true |
| 13006 | 13031 | }, |
| 13032 | + "node_modules/utils-lite": { | |
| 13033 | + "version": "0.1.10", | |
| 13034 | + "resolved": "https://registry.npmmirror.com/utils-lite/-/utils-lite-0.1.10.tgz", | |
| 13035 | + "integrity": "sha512-jlHvdtI8MyWURF/3u+ufIjf1Cs5WjN6WZl9qO8dEkZsVjaI7X5YMUhaCFzkvB69ljt6fo4Dd7V/Oj2NJOFDFOQ==" | |
| 13036 | + }, | |
| 13007 | 13037 | "node_modules/utils-merge": { |
| 13008 | 13038 | "version": "1.0.1", |
| 13009 | 13039 | "resolved": "https://registry.npm.taobao.org/utils-merge/download/utils-merge-1.0.1.tgz", |
| ... | ... | @@ -13021,6 +13051,22 @@ |
| 13021 | 13051 | "uuid": "dist/bin/uuid" |
| 13022 | 13052 | } |
| 13023 | 13053 | }, |
| 13054 | + "node_modules/v-charts": { | |
| 13055 | + "version": "1.19.0", | |
| 13056 | + "resolved": "https://registry.npmmirror.com/v-charts/-/v-charts-1.19.0.tgz", | |
| 13057 | + "integrity": "sha512-vm2HBUmxAsXK0ivwce9LytcpqrItDA5JSPLYVxZXtiuoyhcn80XX1/3dPJd/1GqG1OYv3jfBo1s9ra4q8GowqA==", | |
| 13058 | + "dependencies": { | |
| 13059 | + "echarts-amap": "1.0.0-rc.6", | |
| 13060 | + "echarts-liquidfill": "^2.0.2", | |
| 13061 | + "echarts-wordcloud": "^1.1.3", | |
| 13062 | + "numerify": "1.2.9", | |
| 13063 | + "utils-lite": "0.1.10" | |
| 13064 | + }, | |
| 13065 | + "peerDependencies": { | |
| 13066 | + "echarts": ">3.0.0", | |
| 13067 | + "vue": ">2.0.0" | |
| 13068 | + } | |
| 13069 | + }, | |
| 13024 | 13070 | "node_modules/validate-npm-package-license": { |
| 13025 | 13071 | "version": "3.0.4", |
| 13026 | 13072 | "resolved": "https://registry.npm.taobao.org/validate-npm-package-license/download/validate-npm-package-license-3.0.4.tgz", |
| ... | ... | @@ -17796,12 +17842,28 @@ |
| 17796 | 17842 | }, |
| 17797 | 17843 | "echarts": { |
| 17798 | 17844 | "version": "4.9.0", |
| 17799 | - "resolved": "https://registry.nlark.com/echarts/download/echarts-4.9.0.tgz?cache=0&sync_timestamp=1619495447964&other_urls=https%3A%2F%2Fregistry.nlark.com%2Fecharts%2Fdownload%2Fecharts-4.9.0.tgz", | |
| 17800 | - "integrity": "sha1-qbm6oD8Doqcx5jQMVb77V6nhNH0=", | |
| 17845 | + "resolved": "https://registry.npmmirror.com/echarts/-/echarts-4.9.0.tgz", | |
| 17846 | + "integrity": "sha512-+ugizgtJ+KmsJyyDPxaw2Br5FqzuBnyOWwcxPKO6y0gc5caYcfnEUIlNStx02necw8jmKmTafmpHhGo4XDtEIA==", | |
| 17801 | 17847 | "requires": { |
| 17802 | 17848 | "zrender": "4.3.2" |
| 17803 | 17849 | } |
| 17804 | 17850 | }, |
| 17851 | + "echarts-amap": { | |
| 17852 | + "version": "1.0.0-rc.6", | |
| 17853 | + "resolved": "https://registry.npmmirror.com/echarts-amap/-/echarts-amap-1.0.0-rc.6.tgz", | |
| 17854 | + "integrity": "sha512-cYJCKoQdnkZXrGweYrveU1HruZd1c0KmsF1U8o3FtsvgR2jVL5ZUpGFjMmFtpolHOUFqxizk+s+QBLkYuOWL6Q==" | |
| 17855 | + }, | |
| 17856 | + "echarts-liquidfill": { | |
| 17857 | + "version": "2.0.6", | |
| 17858 | + "resolved": "https://registry.npmmirror.com/echarts-liquidfill/-/echarts-liquidfill-2.0.6.tgz", | |
| 17859 | + "integrity": "sha512-p+AH0O9/BtwXMQQyhjJbMZo+GwRAgWG/DCyK5r27PQzpS0UWrgXu57MyEFc0A8Ub3sRuqEu08BuxwHICBkSWSQ==", | |
| 17860 | + "requires": {} | |
| 17861 | + }, | |
| 17862 | + "echarts-wordcloud": { | |
| 17863 | + "version": "1.1.3", | |
| 17864 | + "resolved": "https://registry.npmmirror.com/echarts-wordcloud/-/echarts-wordcloud-1.1.3.tgz", | |
| 17865 | + "integrity": "sha512-Et8D5xEAoYkidmHun+hEH+2lF9dhCt6D0JJ390vlr2r/1zwhhZAbcL01CEvG93QcMcJpSvSPK8vRiGkTbMHRxg==" | |
| 17866 | + }, | |
| 17805 | 17867 | "ee-first": { |
| 17806 | 17868 | "version": "1.1.1", |
| 17807 | 17869 | "resolved": "https://registry.npm.taobao.org/ee-first/download/ee-first-1.1.1.tgz", |
| ... | ... | @@ -20470,6 +20532,11 @@ |
| 20470 | 20532 | "integrity": "sha1-CXtgK1NCKlIsGvuHkDGDNpQaAR0=", |
| 20471 | 20533 | "dev": true |
| 20472 | 20534 | }, |
| 20535 | + "numerify": { | |
| 20536 | + "version": "1.2.9", | |
| 20537 | + "resolved": "https://registry.npmmirror.com/numerify/-/numerify-1.2.9.tgz", | |
| 20538 | + "integrity": "sha512-X4QzQiytV5ZN3TVLhzbtFzjTarUNnaa1pgNDFqt7u7Nqhxe7FvY2eYrGt4WYHlYXDqgtfC/n/a5nJ2y0LijV8w==" | |
| 20539 | + }, | |
| 20473 | 20540 | "object-assign": { |
| 20474 | 20541 | "version": "4.1.1", |
| 20475 | 20542 | "resolved": "https://registry.npm.taobao.org/object-assign/download/object-assign-4.1.1.tgz", |
| ... | ... | @@ -25327,6 +25394,11 @@ |
| 25327 | 25394 | "integrity": "sha1-ihagXURWV6Oupe7MWxKk+lN5dyw=", |
| 25328 | 25395 | "dev": true |
| 25329 | 25396 | }, |
| 25397 | + "utils-lite": { | |
| 25398 | + "version": "0.1.10", | |
| 25399 | + "resolved": "https://registry.npmmirror.com/utils-lite/-/utils-lite-0.1.10.tgz", | |
| 25400 | + "integrity": "sha512-jlHvdtI8MyWURF/3u+ufIjf1Cs5WjN6WZl9qO8dEkZsVjaI7X5YMUhaCFzkvB69ljt6fo4Dd7V/Oj2NJOFDFOQ==" | |
| 25401 | + }, | |
| 25330 | 25402 | "utils-merge": { |
| 25331 | 25403 | "version": "1.0.1", |
| 25332 | 25404 | "resolved": "https://registry.npm.taobao.org/utils-merge/download/utils-merge-1.0.1.tgz", |
| ... | ... | @@ -25338,6 +25410,18 @@ |
| 25338 | 25410 | "resolved": "https://registry.npmmirror.com/uuid/-/uuid-8.3.2.tgz", |
| 25339 | 25411 | "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==" |
| 25340 | 25412 | }, |
| 25413 | + "v-charts": { | |
| 25414 | + "version": "1.19.0", | |
| 25415 | + "resolved": "https://registry.npmmirror.com/v-charts/-/v-charts-1.19.0.tgz", | |
| 25416 | + "integrity": "sha512-vm2HBUmxAsXK0ivwce9LytcpqrItDA5JSPLYVxZXtiuoyhcn80XX1/3dPJd/1GqG1OYv3jfBo1s9ra4q8GowqA==", | |
| 25417 | + "requires": { | |
| 25418 | + "echarts-amap": "1.0.0-rc.6", | |
| 25419 | + "echarts-liquidfill": "^2.0.2", | |
| 25420 | + "echarts-wordcloud": "^1.1.3", | |
| 25421 | + "numerify": "1.2.9", | |
| 25422 | + "utils-lite": "0.1.10" | |
| 25423 | + } | |
| 25424 | + }, | |
| 25341 | 25425 | "validate-npm-package-license": { |
| 25342 | 25426 | "version": "3.0.4", |
| 25343 | 25427 | "resolved": "https://registry.npm.taobao.org/validate-npm-package-license/download/validate-npm-package-license-3.0.4.tgz", | ... | ... |
web_src/package.json
web_src/src/components/console.vue
0 → 100644
| 1 | +<template> | |
| 2 | + <div id="app" style="width: 100%"> | |
| 3 | + <div class="page-header"> | |
| 4 | + <div class="page-title">控制台</div> | |
| 5 | + </div> | |
| 6 | + <el-row style="width: 100%"> | |
| 7 | + <el-col :xl="{ span: 8 }" :lg="{ span: 8 }" :md="{ span: 12 }" :sm="{ span: 12 }" :xs="{ span: 24 }" > | |
| 8 | + <div class="control-cell" id="ThreadsLoad" > | |
| 9 | + <div style="width:100%; height:100%; "> | |
| 10 | + <consoleCPU ref="consoleCPU"></consoleCPU> | |
| 11 | + </div> | |
| 12 | + </div> | |
| 13 | + </el-col> | |
| 14 | + <el-col :xl="{ span: 8 }" :lg="{ span: 8 }" :md="{ span: 12 }" :sm="{ span: 12 }" :xs="{ span: 24 }" > | |
| 15 | + <div class="control-cell" id="WorkThreadsLoad" > | |
| 16 | + <div style="width:100%; height:100%; "> | |
| 17 | + <consoleMem ref="consoleMem"></consoleMem> | |
| 18 | + </div> | |
| 19 | + </div> | |
| 20 | + </el-col> | |
| 21 | + <el-col :xl="{ span: 8 }" :lg="{ span: 8 }" :md="{ span: 12 }" :sm="{ span: 12 }" :xs="{ span: 24 }" > | |
| 22 | + <div class="control-cell" id="WorkThreadsLoad" > | |
| 23 | + <div style="width:100%; height:100%; "> | |
| 24 | + <consoleNet ref="consoleNet"></consoleNet> | |
| 25 | + </div> | |
| 26 | + </div> | |
| 27 | + </el-col> | |
| 28 | + <el-col :xl="{ span: 8 }" :lg="{ span: 8 }" :md="{ span: 12 }" :sm="{ span: 12 }" :xs="{ span: 24 }" > | |
| 29 | + <div class="control-cell" id="WorkThreadsLoad" > | |
| 30 | + <div style="width:100%; height:100%; "> | |
| 31 | + <consoleCPU></consoleCPU> | |
| 32 | + </div> | |
| 33 | + </div> | |
| 34 | + </el-col> | |
| 35 | + <el-col :xl="{ span: 8 }" :lg="{ span: 8 }" :md="{ span: 12 }" :sm="{ span: 12 }" :xs="{ span: 24 }" > | |
| 36 | + <div class="control-cell" id="WorkThreadsLoad" > | |
| 37 | + <div style="width:100%; height:100%; "> | |
| 38 | + <consoleCPU></consoleCPU> | |
| 39 | + </div> | |
| 40 | + </div> | |
| 41 | + </el-col> | |
| 42 | + <el-col :xl="{ span: 8 }" :lg="{ span: 8 }" :md="{ span: 12 }" :sm="{ span: 12 }" :xs="{ span: 24 }" > | |
| 43 | + <div class="control-cell" id="WorkThreadsLoad" > | |
| 44 | + <div style="width:100%; height:100%; "> | |
| 45 | + <consoleCPU></consoleCPU> | |
| 46 | + </div> | |
| 47 | + </div> | |
| 48 | + </el-col> | |
| 49 | + | |
| 50 | + | |
| 51 | + </el-row> | |
| 52 | + </div> | |
| 53 | +</template> | |
| 54 | + | |
| 55 | +<script> | |
| 56 | +import uiHeader from '../layout/UiHeader.vue' | |
| 57 | +import consoleCPU from './console/ConsoleCPU.vue' | |
| 58 | +import consoleMem from './console/ConsoleMEM.vue' | |
| 59 | +import consoleNet from './console/ConsoleNet.vue' | |
| 60 | + | |
| 61 | +import echarts from 'echarts'; | |
| 62 | + | |
| 63 | +export default { | |
| 64 | + name: 'app', | |
| 65 | + components: { | |
| 66 | + echarts, | |
| 67 | + uiHeader, | |
| 68 | + consoleCPU, | |
| 69 | + consoleMem, | |
| 70 | + consoleNet | |
| 71 | + }, | |
| 72 | + data() { | |
| 73 | + return { | |
| 74 | + timer: null | |
| 75 | + }; | |
| 76 | + }, | |
| 77 | + created() { | |
| 78 | + this.getSystemInfo(); | |
| 79 | + this.loopForSystemInfo(); | |
| 80 | + }, | |
| 81 | + destroyed() { | |
| 82 | + }, | |
| 83 | + methods: { | |
| 84 | + loopForSystemInfo: function (){ | |
| 85 | + if (this.timer != null) { | |
| 86 | + window.clearTimeout(this.timer); | |
| 87 | + } | |
| 88 | + this.timer = setTimeout(()=>{ | |
| 89 | + this.getSystemInfo(); | |
| 90 | + this.timer = null; | |
| 91 | + this.loopForSystemInfo() | |
| 92 | + }, 2000) | |
| 93 | + }, | |
| 94 | + getSystemInfo: function (){ | |
| 95 | + this.$axios({ | |
| 96 | + method: 'get', | |
| 97 | + url: `/api/server/system/info`, | |
| 98 | + }).then( (res)=> { | |
| 99 | + if (res.data.code === 0) { | |
| 100 | + this.$refs.consoleCPU.setData(res.data.data.cpu) | |
| 101 | + this.$refs.consoleMem.setData(res.data.data.mem) | |
| 102 | + this.$refs.consoleNet.setData(res.data.data.net) | |
| 103 | + } | |
| 104 | + }).catch( (error)=> { | |
| 105 | + }); | |
| 106 | + } | |
| 107 | + } | |
| 108 | +}; | |
| 109 | +</script> | |
| 110 | + | |
| 111 | +<style> | |
| 112 | +#app { | |
| 113 | + height: 100%; | |
| 114 | +} | |
| 115 | +.control-cell { | |
| 116 | + padding-top: 10px; | |
| 117 | + padding-left: 5px; | |
| 118 | + padding-right: 10px; | |
| 119 | + height: 360px; | |
| 120 | +} | |
| 121 | +</style> | ... | ... |
web_src/src/components/console/ConsoleCPU.vue
0 → 100644
| 1 | +<template> | |
| 2 | + <div id="consoleCPU" style="width: 100%; height: 100%; background: #FFFFFF; text-align: center"> | |
| 3 | + <ve-line :data="chartData" :extend="extend" width="100%" height="100%" :legend-visible="false"></ve-line> | |
| 4 | + </div> | |
| 5 | +</template> | |
| 6 | + | |
| 7 | +<script> | |
| 8 | + | |
| 9 | + | |
| 10 | +import moment from "moment/moment"; | |
| 11 | + | |
| 12 | +export default { | |
| 13 | + name: 'consoleCPU', | |
| 14 | + data() { | |
| 15 | + return { | |
| 16 | + chartData: { | |
| 17 | + columns: ['time', 'data'], | |
| 18 | + rows: [] | |
| 19 | + }, | |
| 20 | + | |
| 21 | + extend: { | |
| 22 | + title: { | |
| 23 | + show: true, | |
| 24 | + text: "CPU", | |
| 25 | + left: "center", | |
| 26 | + top: 20, | |
| 27 | + | |
| 28 | + }, | |
| 29 | + grid: { | |
| 30 | + show: true, | |
| 31 | + right: "30px", | |
| 32 | + containLabel: true, | |
| 33 | + }, | |
| 34 | + xAxis: { | |
| 35 | + time: "time", | |
| 36 | + max: 'dataMax', | |
| 37 | + boundaryGap: ['20%', '20%'], | |
| 38 | + axisLabel: { | |
| 39 | + formatter:(v)=>{ | |
| 40 | + return moment(v).format("HH:mm:ss"); | |
| 41 | + }, | |
| 42 | + showMaxLabel: true, | |
| 43 | + } | |
| 44 | + }, | |
| 45 | + yAxis: { | |
| 46 | + type: 'value', | |
| 47 | + min: 0, | |
| 48 | + max: 1, | |
| 49 | + splitNumber: 6, | |
| 50 | + position: "left", | |
| 51 | + silent: true, | |
| 52 | + axisLabel: { | |
| 53 | + formatter: (v)=>{ | |
| 54 | + return v*100 + "%"; | |
| 55 | + }, | |
| 56 | + } | |
| 57 | + }, | |
| 58 | + tooltip: { | |
| 59 | + trigger: 'axis', | |
| 60 | + formatter: (data)=>{ | |
| 61 | + console.log(data) | |
| 62 | + return moment(data[0].data[0]).format("HH:mm:ss") + "</br> 使用:" + (data[0].data[1]*100).toFixed(2) + "%"; | |
| 63 | + } | |
| 64 | + }, | |
| 65 | + series: { | |
| 66 | + itemStyle: { | |
| 67 | + color: "#409EFF" | |
| 68 | + }, | |
| 69 | + areaStyle: { | |
| 70 | + color: { | |
| 71 | + type: 'linear', | |
| 72 | + x: 0, | |
| 73 | + y: 0, | |
| 74 | + x2: 0, | |
| 75 | + y2: 1, | |
| 76 | + colorStops: [{ | |
| 77 | + offset: 0, color: '#50a3f8' // 0% 处的颜色 | |
| 78 | + }, { | |
| 79 | + offset: 1, color: '#69b0fa' // 100% 处的颜色 | |
| 80 | + }], | |
| 81 | + global: false // 缺省为 false | |
| 82 | + } | |
| 83 | + } | |
| 84 | + } | |
| 85 | + } | |
| 86 | + }; | |
| 87 | + }, | |
| 88 | + mounted() { | |
| 89 | + // setInterval(()=>{ | |
| 90 | + // // console.log(111111) | |
| 91 | + // for (let i = 0; i < this.chartData.rows.length; i++) { | |
| 92 | + // this.chartData.rows[i].销售额 += 1000; | |
| 93 | + // } | |
| 94 | + // },1000) | |
| 95 | + }, | |
| 96 | + destroyed() { | |
| 97 | + }, | |
| 98 | + methods: { | |
| 99 | + setData: function(data) { | |
| 100 | + this.chartData .rows = data; | |
| 101 | + } | |
| 102 | + | |
| 103 | + } | |
| 104 | +}; | |
| 105 | +</script> | ... | ... |
web_src/src/components/console/ConsoleMEM.vue
0 → 100644
| 1 | +<template> | |
| 2 | + <div id="ConsoleMEM" style="width: 100%; height: 100%; background: #FFFFFF; text-align: center"> | |
| 3 | + <ve-line :data="chartData" :extend="extend" width="100%" height="100%" :legend-visible="false"></ve-line> | |
| 4 | + </div> | |
| 5 | +</template> | |
| 6 | + | |
| 7 | +<script> | |
| 8 | + | |
| 9 | + | |
| 10 | +import moment from "moment/moment"; | |
| 11 | + | |
| 12 | +export default { | |
| 13 | + name: 'ConsoleMEM', | |
| 14 | + data() { | |
| 15 | + return { | |
| 16 | + chartData: { | |
| 17 | + columns: ['time', 'data'], | |
| 18 | + rows: [] | |
| 19 | + }, | |
| 20 | + | |
| 21 | + extend: { | |
| 22 | + title: { | |
| 23 | + show: true, | |
| 24 | + text: "内存", | |
| 25 | + left: "center", | |
| 26 | + top: 20, | |
| 27 | + | |
| 28 | + }, | |
| 29 | + grid: { | |
| 30 | + show: true, | |
| 31 | + right: "30px", | |
| 32 | + containLabel: true, | |
| 33 | + }, | |
| 34 | + xAxis: { | |
| 35 | + time: "time", | |
| 36 | + max: 'dataMax', | |
| 37 | + boundaryGap: ['20%', '20%'], | |
| 38 | + axisLabel: { | |
| 39 | + formatter:(v)=>{ | |
| 40 | + return moment(v).format("HH:mm:ss"); | |
| 41 | + }, | |
| 42 | + showMaxLabel: true, | |
| 43 | + } | |
| 44 | + }, | |
| 45 | + yAxis: { | |
| 46 | + type: 'value', | |
| 47 | + min: 0, | |
| 48 | + max: 1, | |
| 49 | + splitNumber: 6, | |
| 50 | + position: "left", | |
| 51 | + silent: true, | |
| 52 | + axisLabel: { | |
| 53 | + formatter: (v)=>{ | |
| 54 | + return v*100 + "%"; | |
| 55 | + }, | |
| 56 | + } | |
| 57 | + }, | |
| 58 | + tooltip: { | |
| 59 | + trigger: 'axis', | |
| 60 | + formatter: (data)=>{ | |
| 61 | + console.log(data) | |
| 62 | + return moment(data[0].data[0]).format("HH:mm:ss") + "</br> 使用:" + (data[0].data[1]*100).toFixed(2) + "%"; | |
| 63 | + } | |
| 64 | + }, | |
| 65 | + series: { | |
| 66 | + itemStyle: { | |
| 67 | + color: "#409EFF" | |
| 68 | + }, | |
| 69 | + areaStyle: { | |
| 70 | + color: { | |
| 71 | + type: 'linear', | |
| 72 | + x: 0, | |
| 73 | + y: 0, | |
| 74 | + x2: 0, | |
| 75 | + y2: 1, | |
| 76 | + colorStops: [{ | |
| 77 | + offset: 0, color: '#50a3f8' // 0% 处的颜色 | |
| 78 | + }, { | |
| 79 | + offset: 1, color: '#69b0fa' // 100% 处的颜色 | |
| 80 | + }], | |
| 81 | + global: false // 缺省为 false | |
| 82 | + } | |
| 83 | + } | |
| 84 | + } | |
| 85 | + } | |
| 86 | + }; | |
| 87 | + }, | |
| 88 | + mounted() { | |
| 89 | + // setInterval(()=>{ | |
| 90 | + // // console.log(111111) | |
| 91 | + // for (let i = 0; i < this.chartData.rows.length; i++) { | |
| 92 | + // this.chartData.rows[i].销售额 += 1000; | |
| 93 | + // } | |
| 94 | + // },1000) | |
| 95 | + }, | |
| 96 | + destroyed() { | |
| 97 | + }, | |
| 98 | + methods: { | |
| 99 | + setData: function(data) { | |
| 100 | + this.chartData .rows = data; | |
| 101 | + } | |
| 102 | + | |
| 103 | + } | |
| 104 | +}; | |
| 105 | +</script> | ... | ... |
web_src/src/components/console/ConsoleMediaServer.vue
0 → 100644
| 1 | +<template> | |
| 2 | + <div id="ConsoleMediaServer" style="width: 100%; height: 100%; background: #FFFFFF; text-align: center"> | |
| 3 | + <ve-histogram :data="chartData" :extend="extend" :settings="chartSettings" width="100%" height="100%" ></ve-histogram> | |
| 4 | + </div> | |
| 5 | +</template> | |
| 6 | + | |
| 7 | +<script> | |
| 8 | + | |
| 9 | + | |
| 10 | +import moment from "moment/moment"; | |
| 11 | + | |
| 12 | +export default { | |
| 13 | + name: 'ConsoleMediaServer', | |
| 14 | + data() { | |
| 15 | + return { | |
| 16 | + chartData: { | |
| 17 | + columns: ['time', 'in', 'out'], | |
| 18 | + rows: [ | |
| 19 | + ] | |
| 20 | + }, | |
| 21 | + chartSettings: { | |
| 22 | + area: true, | |
| 23 | + labelMap: { | |
| 24 | + 'in': '下载', | |
| 25 | + 'out': '上传' | |
| 26 | + }, | |
| 27 | + }, | |
| 28 | + extend: { | |
| 29 | + title: { | |
| 30 | + show: true, | |
| 31 | + text: "网络", | |
| 32 | + left: "center", | |
| 33 | + top: 20, | |
| 34 | + | |
| 35 | + }, | |
| 36 | + grid: { | |
| 37 | + show: true, | |
| 38 | + right: "30px", | |
| 39 | + containLabel: true, | |
| 40 | + }, | |
| 41 | + xAxis: { | |
| 42 | + time: "time", | |
| 43 | + max: 'dataMax', | |
| 44 | + boundaryGap: ['20%', '20%'], | |
| 45 | + axisLabel: { | |
| 46 | + formatter:(v)=>{ | |
| 47 | + return moment(v).format("HH:mm:ss"); | |
| 48 | + }, | |
| 49 | + showMaxLabel: true, | |
| 50 | + }, | |
| 51 | + }, | |
| 52 | + tooltip: { | |
| 53 | + trigger: 'axis', | |
| 54 | + formatter: (data)=>{ | |
| 55 | + console.log(parseFloat(data[0].data[1]).toFixed(2)) | |
| 56 | + console.log(parseFloat(data[1].data[1]).toFixed(2)) | |
| 57 | + console.log("############") | |
| 58 | + return "下载:" + parseFloat(data[0].data[1]).toFixed(2) + "Mbps" + "</br> 上传:" + parseFloat(data[1].data[1]).toFixed(2) + "Mbps"; | |
| 59 | + } | |
| 60 | + }, | |
| 61 | + legend: { | |
| 62 | + left: "center", | |
| 63 | + bottom: "15px", | |
| 64 | + } | |
| 65 | + } | |
| 66 | + }; | |
| 67 | + }, | |
| 68 | + mounted() { | |
| 69 | + // setInterval(()=>{ | |
| 70 | + // // console.log(111111) | |
| 71 | + // for (let i = 0; i < this.chartData.rows.length; i++) { | |
| 72 | + // this.chartData.rows[i].销售额 += 1000; | |
| 73 | + // } | |
| 74 | + // },1000) | |
| 75 | + }, | |
| 76 | + destroyed() { | |
| 77 | + }, | |
| 78 | + methods: { | |
| 79 | + setData: function(data) { | |
| 80 | + console.log(data) | |
| 81 | + this.chartData .rows = data; | |
| 82 | + } | |
| 83 | + | |
| 84 | + } | |
| 85 | +}; | |
| 86 | +</script> | ... | ... |
web_src/src/components/console/ConsoleNet.vue
0 → 100644
| 1 | +<template> | |
| 2 | + <div id="ConsoleNet" style="width: 100%; height: 100%; background: #FFFFFF; text-align: center"> | |
| 3 | + <ve-line :data="chartData" :extend="extend" :settings="chartSettings" width="100%" height="100%" ></ve-line> | |
| 4 | + </div> | |
| 5 | +</template> | |
| 6 | + | |
| 7 | +<script> | |
| 8 | + | |
| 9 | + | |
| 10 | +import moment from "moment/moment"; | |
| 11 | + | |
| 12 | +export default { | |
| 13 | + name: 'ConsoleNet', | |
| 14 | + data() { | |
| 15 | + return { | |
| 16 | + chartData: { | |
| 17 | + columns: ['time', 'in', 'out'], | |
| 18 | + rows: [] | |
| 19 | + }, | |
| 20 | + chartSettings: { | |
| 21 | + area: true, | |
| 22 | + labelMap: { | |
| 23 | + 'in': '下载', | |
| 24 | + 'out': '上传' | |
| 25 | + }, | |
| 26 | + }, | |
| 27 | + extend: { | |
| 28 | + title: { | |
| 29 | + show: true, | |
| 30 | + text: "网络", | |
| 31 | + left: "center", | |
| 32 | + top: 20, | |
| 33 | + | |
| 34 | + }, | |
| 35 | + grid: { | |
| 36 | + show: true, | |
| 37 | + right: "30px", | |
| 38 | + containLabel: true, | |
| 39 | + }, | |
| 40 | + xAxis: { | |
| 41 | + time: "time", | |
| 42 | + max: 'dataMax', | |
| 43 | + boundaryGap: ['20%', '20%'], | |
| 44 | + axisLabel: { | |
| 45 | + formatter:(v)=>{ | |
| 46 | + return moment(v).format("HH:mm:ss"); | |
| 47 | + }, | |
| 48 | + showMaxLabel: true, | |
| 49 | + }, | |
| 50 | + }, | |
| 51 | + tooltip: { | |
| 52 | + trigger: 'axis', | |
| 53 | + formatter: (data)=>{ | |
| 54 | + console.log(parseFloat(data[0].data[1]).toFixed(2)) | |
| 55 | + console.log(parseFloat(data[1].data[1]).toFixed(2)) | |
| 56 | + console.log("############") | |
| 57 | + return "下载:" + parseFloat(data[0].data[1]).toFixed(2) + "Mbps" + "</br> 上传:" + parseFloat(data[1].data[1]).toFixed(2) + "Mbps"; | |
| 58 | + } | |
| 59 | + }, | |
| 60 | + legend: { | |
| 61 | + left: "center", | |
| 62 | + bottom: "15px", | |
| 63 | + } | |
| 64 | + } | |
| 65 | + }; | |
| 66 | + }, | |
| 67 | + mounted() { | |
| 68 | + // setInterval(()=>{ | |
| 69 | + // // console.log(111111) | |
| 70 | + // for (let i = 0; i < this.chartData.rows.length; i++) { | |
| 71 | + // this.chartData.rows[i].销售额 += 1000; | |
| 72 | + // } | |
| 73 | + // },1000) | |
| 74 | + }, | |
| 75 | + destroyed() { | |
| 76 | + }, | |
| 77 | + methods: { | |
| 78 | + setData: function(data) { | |
| 79 | + console.log(data) | |
| 80 | + this.chartData .rows = data; | |
| 81 | + } | |
| 82 | + | |
| 83 | + } | |
| 84 | +}; | |
| 85 | +</script> | ... | ... |
web_src/src/components/control.vue deleted
100644 → 0
| 1 | -<template> | |
| 2 | - <div id="app" style="width: 100%"> | |
| 3 | - <div class="page-header"> | |
| 4 | - <div class="page-title">控制台</div> | |
| 5 | - <div class="page-header-btn"> | |
| 6 | - 节点选择: | |
| 7 | - <el-select size="mini" @change="chooseMediaChange" style="width: 18rem; margin-right: 8rem;" | |
| 8 | - v-model="mediaServerChoose" placeholder="请选择" default-first-option> | |
| 9 | - <el-option | |
| 10 | - v-for="item in mediaServerList" | |
| 11 | - :key="item.id" | |
| 12 | - :label="item.id + '( ' + item.streamIp + ' )'" | |
| 13 | - :value="item.id"> | |
| 14 | - </el-option> | |
| 15 | - </el-select> | |
| 16 | - <span>{{ loadCount }}</span> | |
| 17 | - </div> | |
| 18 | - <div class="page-header-btn"> | |
| 19 | - <el-popover placement="bottom" width="900" height="300" trigger="click"> | |
| 20 | - <div style="height: 600px; overflow:auto; padding: 20px"> | |
| 21 | - <el-descriptions v-for="(value, key, index) in serverConfig" :key="key" border :column="1" | |
| 22 | - style="margin-bottom: 1rem"> | |
| 23 | - <template slot="title"> | |
| 24 | - {{ key }} | |
| 25 | - </template> | |
| 26 | - <el-descriptions-item v-for="(value1, key1, index1) in serverConfig[key]" :key="key1"> | |
| 27 | - <template slot="label"> | |
| 28 | - {{ getMediaKeyNameFromKey(key1) }} | |
| 29 | - </template> | |
| 30 | - {{ value1 }} | |
| 31 | - </el-descriptions-item> | |
| 32 | - </el-descriptions> | |
| 33 | - </div> | |
| 34 | - <el-button type="primary" slot="reference" size="mini" @click="getServerConfig()">媒体服务器配置</el-button> | |
| 35 | - </el-popover> | |
| 36 | - <el-popover placement="bottom" width="900" height="300" trigger="click"> | |
| 37 | - <div style="height: 600px;overflow:auto; padding: 20px"> | |
| 38 | - <el-descriptions title="国标配置" border :column="1"> | |
| 39 | - <template slot="extra"> | |
| 40 | - <el-button style="float: right;" type="primary" size="mini" icon="el-icon-document-copy" title="点击拷贝" | |
| 41 | - v-clipboard="JSON.stringify(wvpServerConfig.sip)|| ''" | |
| 42 | - @success="$message({type:'success', message:'成功拷贝到粘贴板'})"></el-button> | |
| 43 | - </template> | |
| 44 | - <el-descriptions-item v-for="(value, key, index) in wvpServerConfig.sip" :key="key"> | |
| 45 | - <template slot="label"> | |
| 46 | - {{ getNameFromKey(key) }} | |
| 47 | - </template> | |
| 48 | - {{ value }} | |
| 49 | - </el-descriptions-item> | |
| 50 | - </el-descriptions> | |
| 51 | - | |
| 52 | - <div style="margin-top: 1rem"> | |
| 53 | - <el-descriptions title="基础配置" border :column="1"> | |
| 54 | - <template slot="extra"> | |
| 55 | - <el-button style="float: right;" type="primary" size="mini" icon="el-icon-document-copy" title="点击拷贝" | |
| 56 | - v-clipboard="JSON.stringify(wvpServerConfig.base)|| ''" | |
| 57 | - @success="$message({type:'success', message:'成功拷贝到粘贴板'})"></el-button> | |
| 58 | - </template> | |
| 59 | - <el-descriptions-item v-for="(value, key, index) in wvpServerConfig.base" :key="key"> | |
| 60 | - <template slot="label"> | |
| 61 | - {{ getNameFromKey(key) }} | |
| 62 | - </template> | |
| 63 | - <div v-if="key === 'interfaceAuthenticationExcludes'"> | |
| 64 | - <el-dropdown> | |
| 65 | - <span class="el-dropdown-link"> | |
| 66 | - 查看<i class="el-icon-arrow-down el-icon--right"></i> | |
| 67 | - </span> | |
| 68 | - <el-dropdown-menu slot="dropdown"> | |
| 69 | - <el-dropdown-item | |
| 70 | - v-for="(value, key, index) in wvpServerConfig.base.interfaceAuthenticationExcludes" | |
| 71 | - :key="key">{{ value }} | |
| 72 | - </el-dropdown-item> | |
| 73 | - </el-dropdown-menu> | |
| 74 | - </el-dropdown> | |
| 75 | - </div> | |
| 76 | - <div v-if="key !== 'interfaceAuthenticationExcludes'"> | |
| 77 | - <div v-if="value === true"> | |
| 78 | - 已启用 | |
| 79 | - </div> | |
| 80 | - <div v-if="value === false"> | |
| 81 | - 未启用 | |
| 82 | - </div> | |
| 83 | - <div v-if="value !== true && value !== false"> | |
| 84 | - {{ value }} | |
| 85 | - </div> | |
| 86 | - </div> | |
| 87 | - | |
| 88 | - </el-descriptions-item> | |
| 89 | - </el-descriptions> | |
| 90 | - </div> | |
| 91 | - <div style="margin-top: 1rem"> | |
| 92 | - <el-descriptions title="版本信息" border :column="1"> | |
| 93 | - <template slot="extra"> | |
| 94 | - <el-button style="float: right;" type="primary" size="mini" icon="el-icon-document-copy" title="点击拷贝" | |
| 95 | - v-clipboard="JSON.stringify(wvpServerVersion) || ''" | |
| 96 | - @success="$message({type:'success', message:'成功拷贝到粘贴板'})"></el-button> | |
| 97 | - </template> | |
| 98 | - <el-descriptions-item v-for="(value, key, index) in wvpServerVersion" :key="key"> | |
| 99 | - <template slot="label"> | |
| 100 | - {{ getNameFromKey(key) }} | |
| 101 | - </template> | |
| 102 | - {{ value }} | |
| 103 | - </el-descriptions-item> | |
| 104 | - </el-descriptions> | |
| 105 | - | |
| 106 | - | |
| 107 | - </div> | |
| 108 | - </div> | |
| 109 | - <el-button type="primary" slot="reference" size="mini" @click="getWVPServerConfig()">信令服务器配置</el-button> | |
| 110 | - </el-popover> | |
| 111 | - <el-button style="margin-left: 1rem;" type="danger" size="mini" @click="reStartServer()">重启媒体服务器</el-button> | |
| 112 | - </div> | |
| 113 | - </div> | |
| 114 | - <!-- <div style="background-color: #FFFFFF; margin-bottom: 1rem; position: relative; padding: 0.5rem; text-align: left;">--> | |
| 115 | - <!-- <span style="font-size: 1rem; font-weight: bold;">控制台</span>--> | |
| 116 | - <!-- <div style="position: absolute; right: 17rem; top: 0.3rem;">--> | |
| 117 | - <!-- 节点选择:--> | |
| 118 | - <!-- <el-select size="mini" @change="chooseMediaChange" style="width: 18rem; margin-right: 8rem;"--> | |
| 119 | - <!-- v-model="mediaServerChoose" placeholder="请选择" default-first-option>--> | |
| 120 | - <!-- <el-option--> | |
| 121 | - <!-- v-for="item in mediaServerList"--> | |
| 122 | - <!-- :key="item.id"--> | |
| 123 | - <!-- :label="item.id + '( ' + item.streamIp + ' )'"--> | |
| 124 | - <!-- :value="item.id">--> | |
| 125 | - <!-- </el-option>--> | |
| 126 | - <!-- </el-select>--> | |
| 127 | - <!-- <span>{{ loadCount }}</span>--> | |
| 128 | - <!-- </div>--> | |
| 129 | - <!-- <div style="position: absolute; right: 1rem; top: 0.3rem;">--> | |
| 130 | - <!-- <el-popover placement="bottom" width="900" height="300" trigger="click">--> | |
| 131 | - <!-- <div style="height: 600px; overflow:auto; padding: 20px">--> | |
| 132 | - <!-- <el-descriptions v-for="(value, key, index) in serverConfig" :key="key" border :column="1"--> | |
| 133 | - <!-- style="margin-bottom: 1rem">--> | |
| 134 | - <!-- <template slot="title">--> | |
| 135 | - <!-- {{ key }}--> | |
| 136 | - <!-- </template>--> | |
| 137 | - <!-- <el-descriptions-item v-for="(value1, key1, index1) in serverConfig[key]" :key="key1">--> | |
| 138 | - <!-- <template slot="label">--> | |
| 139 | - <!-- {{ getMediaKeyNameFromKey(key1) }}--> | |
| 140 | - <!-- </template>--> | |
| 141 | - <!-- {{ value1 }}--> | |
| 142 | - <!-- </el-descriptions-item>--> | |
| 143 | - <!-- </el-descriptions>--> | |
| 144 | - <!-- </div>--> | |
| 145 | - <!-- <el-button type="primary" slot="reference" size="mini" @click="getServerConfig()">媒体服务器配置</el-button>--> | |
| 146 | - <!-- </el-popover>--> | |
| 147 | - <!-- <el-popover placement="bottom" width="900" height="300" trigger="click">--> | |
| 148 | - <!-- <div style="height: 600px;overflow:auto; padding: 20px">--> | |
| 149 | - <!-- <el-descriptions title="国标配置" border :column="1">--> | |
| 150 | - <!-- <template slot="extra">--> | |
| 151 | - <!-- <el-button style="float: right;" type="primary" size="mini" icon="el-icon-document-copy" title="点击拷贝"--> | |
| 152 | - <!-- v-clipboard="JSON.stringify(wvpServerConfig.sip)|| ''"--> | |
| 153 | - <!-- @success="$message({type:'success', message:'成功拷贝到粘贴板'})"></el-button>--> | |
| 154 | - <!-- </template>--> | |
| 155 | - <!-- <el-descriptions-item v-for="(value, key, index) in wvpServerConfig.sip" :key="key">--> | |
| 156 | - <!-- <template slot="label">--> | |
| 157 | - <!-- {{ getNameFromKey(key) }}--> | |
| 158 | - <!-- </template>--> | |
| 159 | - <!-- {{ value }}--> | |
| 160 | - <!-- </el-descriptions-item>--> | |
| 161 | - <!-- </el-descriptions>--> | |
| 162 | - | |
| 163 | - <!-- <div style="margin-top: 1rem">--> | |
| 164 | - <!-- <el-descriptions title="基础配置" border :column="1">--> | |
| 165 | - <!-- <template slot="extra">--> | |
| 166 | - <!-- <el-button style="float: right;" type="primary" size="mini" icon="el-icon-document-copy" title="点击拷贝"--> | |
| 167 | - <!-- v-clipboard="JSON.stringify(wvpServerConfig.base)|| ''"--> | |
| 168 | - <!-- @success="$message({type:'success', message:'成功拷贝到粘贴板'})"></el-button>--> | |
| 169 | - <!-- </template>--> | |
| 170 | - <!-- <el-descriptions-item v-for="(value, key, index) in wvpServerConfig.base" :key="key">--> | |
| 171 | - <!-- <template slot="label">--> | |
| 172 | - <!-- {{ getNameFromKey(key) }}--> | |
| 173 | - <!-- </template>--> | |
| 174 | - <!-- <div v-if="key === 'interfaceAuthenticationExcludes'">--> | |
| 175 | - <!-- <el-dropdown>--> | |
| 176 | - <!-- <span class="el-dropdown-link">--> | |
| 177 | - <!-- 查看<i class="el-icon-arrow-down el-icon--right"></i>--> | |
| 178 | - <!-- </span>--> | |
| 179 | - <!-- <el-dropdown-menu slot="dropdown">--> | |
| 180 | - <!-- <el-dropdown-item--> | |
| 181 | - <!-- v-for="(value, key, index) in wvpServerConfig.base.interfaceAuthenticationExcludes"--> | |
| 182 | - <!-- :key="key">{{ value }}--> | |
| 183 | - <!-- </el-dropdown-item>--> | |
| 184 | - <!-- </el-dropdown-menu>--> | |
| 185 | - <!-- </el-dropdown>--> | |
| 186 | - <!-- </div>--> | |
| 187 | - <!-- <div v-if="key !== 'interfaceAuthenticationExcludes'">--> | |
| 188 | - <!-- <div v-if="value === true">--> | |
| 189 | - <!-- 已启用--> | |
| 190 | - <!-- </div>--> | |
| 191 | - <!-- <div v-if="value === false">--> | |
| 192 | - <!-- 未启用--> | |
| 193 | - <!-- </div>--> | |
| 194 | - <!-- <div v-if="value !== true && value !== false">--> | |
| 195 | - <!-- {{ value }}--> | |
| 196 | - <!-- </div>--> | |
| 197 | - <!-- </div>--> | |
| 198 | - | |
| 199 | - <!-- </el-descriptions-item>--> | |
| 200 | - <!-- </el-descriptions>--> | |
| 201 | - <!-- </div>--> | |
| 202 | - <!-- <div style="margin-top: 1rem">--> | |
| 203 | - <!-- <el-descriptions title="版本信息" border :column="1">--> | |
| 204 | - <!-- <template slot="extra">--> | |
| 205 | - <!-- <el-button style="float: right;" type="primary" size="mini" icon="el-icon-document-copy" title="点击拷贝"--> | |
| 206 | - <!-- v-clipboard="JSON.stringify(wvpServerVersion) || ''"--> | |
| 207 | - <!-- @success="$message({type:'success', message:'成功拷贝到粘贴板'})"></el-button>--> | |
| 208 | - <!-- </template>--> | |
| 209 | - <!-- <el-descriptions-item v-for="(value, key, index) in wvpServerVersion" :key="key">--> | |
| 210 | - <!-- <template slot="label">--> | |
| 211 | - <!-- {{ getNameFromKey(key) }}--> | |
| 212 | - <!-- </template>--> | |
| 213 | - <!-- {{ value }}--> | |
| 214 | - <!-- </el-descriptions-item>--> | |
| 215 | - <!-- </el-descriptions>--> | |
| 216 | - | |
| 217 | - | |
| 218 | - <!-- </div>--> | |
| 219 | - <!-- </div>--> | |
| 220 | - <!-- <el-button type="primary" slot="reference" size="mini" @click="getWVPServerConfig()">信令服务器配置</el-button>--> | |
| 221 | - <!-- </el-popover>--> | |
| 222 | - <!-- <el-button style="margin-left: 1rem;" type="danger" size="mini" @click="reStartServer()">重启媒体服务器</el-button>--> | |
| 223 | - <!-- </div>--> | |
| 224 | - <!-- </div>--> | |
| 225 | - <el-row style="width: 100%"> | |
| 226 | - <el-col :span="12"> | |
| 227 | - <div class="control-table" id="ThreadsLoad" style="margin-right:10px;">table1</div> | |
| 228 | - </el-col> | |
| 229 | - <el-col :span="12"> | |
| 230 | - <div class="control-table" id="WorkThreadsLoad" style="margin-left:10px;">table2</div> | |
| 231 | - </el-col> | |
| 232 | - </el-row> | |
| 233 | - <el-table :data="allSessionData" style="margin-top: 1rem;"> | |
| 234 | - <el-table-column prop="peer_ip" label="远端"></el-table-column> | |
| 235 | - <el-table-column prop="local_ip" label="本地"></el-table-column> | |
| 236 | - <el-table-column prop="typeid" label="类型"></el-table-column> | |
| 237 | - <el-table-column align="right"> | |
| 238 | - <template v-slot:default="scope"> | |
| 239 | - <el-button size="mini" icon="el-icon-refresh-right" circle @click="getAllSession()"></el-button> | |
| 240 | - <el-button @click.native.prevent="deleteRow(scope.$index, allSessionData)" type="text" size="small">移除 | |
| 241 | - </el-button> | |
| 242 | - </template> | |
| 243 | - </el-table-column> | |
| 244 | - </el-table> | |
| 245 | - </div> | |
| 246 | -</template> | |
| 247 | - | |
| 248 | -<script> | |
| 249 | -import uiHeader from '../layout/UiHeader.vue' | |
| 250 | -import MediaServer from './service/MediaServer' | |
| 251 | - | |
| 252 | -import echarts from 'echarts'; | |
| 253 | - | |
| 254 | -export default { | |
| 255 | - name: 'app', | |
| 256 | - components: { | |
| 257 | - echarts, | |
| 258 | - uiHeader | |
| 259 | - }, | |
| 260 | - data() { | |
| 261 | - return { | |
| 262 | - tableOption: { | |
| 263 | - // legend: {}, | |
| 264 | - xAxis: {}, | |
| 265 | - yAxis: {}, | |
| 266 | - label: {}, | |
| 267 | - tooltip: {}, | |
| 268 | - dataZoom: [], | |
| 269 | - series: [] | |
| 270 | - }, | |
| 271 | - table1Option: { | |
| 272 | - // legend: {}, | |
| 273 | - xAxis: {}, | |
| 274 | - yAxis: {}, | |
| 275 | - label: {}, | |
| 276 | - tooltip: {}, | |
| 277 | - series: [] | |
| 278 | - }, | |
| 279 | - mChart: null, | |
| 280 | - mChart1: null, | |
| 281 | - charZoomStart: 0, | |
| 282 | - charZoomEnd: 100, | |
| 283 | - chartInterval: 0, //更新图表统计图定时任务标识 | |
| 284 | - allSessionData: [], | |
| 285 | - visible: false, | |
| 286 | - wvpVisible: false, | |
| 287 | - serverConfig: {}, | |
| 288 | - wvpServerConfig: {}, | |
| 289 | - wvpServerVersion: {}, | |
| 290 | - mediaServer: new MediaServer(), | |
| 291 | - mediaServerChoose: null, | |
| 292 | - loadCount: 0, | |
| 293 | - mediaServerList: [] | |
| 294 | - }; | |
| 295 | - }, | |
| 296 | - mounted() { | |
| 297 | - this.initTable() | |
| 298 | - this.chartInterval = setInterval(this.updateData, 3000); | |
| 299 | - this.mediaServer.getOnlineMediaServerList((data) => { | |
| 300 | - this.mediaServerList = data.data; | |
| 301 | - if (this.mediaServerList && this.mediaServerList.length > 0) { | |
| 302 | - this.mediaServerChoose = this.mediaServerList[0].id | |
| 303 | - this.loadCount = this.mediaServerList[0].count; | |
| 304 | - this.updateData(); | |
| 305 | - } | |
| 306 | - }) | |
| 307 | - }, | |
| 308 | - destroyed() { | |
| 309 | - clearInterval(this.chartInterval); //释放定时任务 | |
| 310 | - }, | |
| 311 | - methods: { | |
| 312 | - chooseMediaChange: function (val) { | |
| 313 | - this.loadCount = 0 | |
| 314 | - this.initTable() | |
| 315 | - this.updateData(); | |
| 316 | - }, | |
| 317 | - updateData: function () { | |
| 318 | - this.getThreadsLoad(); | |
| 319 | - this.getLoadCount(); | |
| 320 | - this.getAllSession(); | |
| 321 | - }, | |
| 322 | - /** | |
| 323 | - * 获取线程状态 | |
| 324 | - */ | |
| 325 | - getThreadsLoad: function () { | |
| 326 | - let that = this; | |
| 327 | - if (!!that.mediaServerChoose) { | |
| 328 | - this.$axios({ | |
| 329 | - method: 'get', | |
| 330 | - url: '/zlm/' + that.mediaServerChoose + '/index/api/getThreadsLoad' | |
| 331 | - }).then(function (res) { | |
| 332 | - if (res.data.code === 0) { | |
| 333 | - that.tableOption.xAxis.data.push(new Date().toLocaleTimeString('chinese', { | |
| 334 | - hour12: false | |
| 335 | - })); | |
| 336 | - that.table1Option.xAxis.data.push(new Date().toLocaleTimeString('chinese', { | |
| 337 | - hour12: false | |
| 338 | - })); | |
| 339 | - | |
| 340 | - for (var i = 0; i < res.data.data.length; i++) { | |
| 341 | - if (that.tableOption.series[i] === undefined) { | |
| 342 | - let data = { | |
| 343 | - data: [], | |
| 344 | - type: 'line' | |
| 345 | - }; | |
| 346 | - let data1 = { | |
| 347 | - data: [], | |
| 348 | - type: 'line' | |
| 349 | - }; | |
| 350 | - data.data.push(res.data.data[i].delay); | |
| 351 | - data1.data.push(res.data.data[i].load); | |
| 352 | - that.tableOption.series.push(data); | |
| 353 | - that.table1Option.series.push(data1); | |
| 354 | - } else { | |
| 355 | - that.tableOption.series[i].data.push(res.data.data[i].delay); | |
| 356 | - that.table1Option.series[i].data.push(res.data.data[i].load); | |
| 357 | - } | |
| 358 | - } | |
| 359 | - that.tableOption.dataZoom[0].start = that.charZoomStart; | |
| 360 | - that.tableOption.dataZoom[0].end = that.charZoomEnd; | |
| 361 | - that.table1Option.dataZoom[0].start = that.charZoomStart; | |
| 362 | - that.table1Option.dataZoom[0].end = that.charZoomEnd; | |
| 363 | - //that.myChart = echarts.init(document.getElementById('ThreadsLoad')); | |
| 364 | - that.myChart.setOption(that.tableOption, true); | |
| 365 | - // that.myChart1 = echarts.init(document.getElementById('WorkThreadsLoad')); | |
| 366 | - that.myChart1.setOption(that.table1Option, true); | |
| 367 | - that.$nextTick(() => { | |
| 368 | - that.myChart.resize() | |
| 369 | - that.myChart1.resize() | |
| 370 | - }) | |
| 371 | - } | |
| 372 | - }); | |
| 373 | - } | |
| 374 | - | |
| 375 | - }, | |
| 376 | - getLoadCount: function () { | |
| 377 | - let that = this; | |
| 378 | - if (!!that.mediaServerChoose) { | |
| 379 | - that.mediaServer.getMediaServer(that.mediaServerChoose, (data) => { | |
| 380 | - if (data.code == 0) { | |
| 381 | - that.loadCount = data.data.count | |
| 382 | - } | |
| 383 | - }) | |
| 384 | - } | |
| 385 | - }, | |
| 386 | - initTable: function () { | |
| 387 | - let that = this; | |
| 388 | - this.tableOption.xAxis = { | |
| 389 | - type: 'category', | |
| 390 | - data: [], // x轴数据 | |
| 391 | - name: '时间', // x轴名称 | |
| 392 | - // x轴名称样式 | |
| 393 | - nameTextStyle: { | |
| 394 | - fontWeight: 300, | |
| 395 | - fontSize: 15 | |
| 396 | - } | |
| 397 | - }; | |
| 398 | - this.tableOption.yAxis = { | |
| 399 | - type: 'value', | |
| 400 | - name: '延迟率', // y轴名称 | |
| 401 | - boundaryGap: [0, '100%'], | |
| 402 | - max: 100, | |
| 403 | - axisLabel: { | |
| 404 | - show: true, | |
| 405 | - interval: 'auto', | |
| 406 | - formatter: '{value} %' | |
| 407 | - }, | |
| 408 | - // y轴名称样式 | |
| 409 | - nameTextStyle: { | |
| 410 | - fontWeight: 300, | |
| 411 | - fontSize: 15 | |
| 412 | - } | |
| 413 | - }; | |
| 414 | - this.tableOption.dataZoom = [{ | |
| 415 | - show: true, | |
| 416 | - start: this.charZoomStart, | |
| 417 | - end: this.charZoomEnd | |
| 418 | - }]; | |
| 419 | - this.myChart = echarts.init(document.getElementById('ThreadsLoad')); | |
| 420 | - this.myChart.setOption(this.tableOption); | |
| 421 | - this.myChart.on('dataZoom', function (event) { | |
| 422 | - if (event.batch) { | |
| 423 | - that.charZoomStart = event.batch[0].start; | |
| 424 | - that.charZoomEnd = event.batch[0].end; | |
| 425 | - } else { | |
| 426 | - that.charZoomStart = event.start; | |
| 427 | - that.charZoomEnd = event.end; | |
| 428 | - } | |
| 429 | - }); | |
| 430 | - | |
| 431 | - this.table1Option.xAxis = { | |
| 432 | - type: 'category', | |
| 433 | - data: [], // x轴数据 | |
| 434 | - name: '时间', // x轴名称 | |
| 435 | - // x轴名称样式 | |
| 436 | - nameTextStyle: { | |
| 437 | - fontWeight: 300, | |
| 438 | - fontSize: 15 | |
| 439 | - } | |
| 440 | - }; | |
| 441 | - this.table1Option.yAxis = { | |
| 442 | - type: 'value', | |
| 443 | - name: '负载率', // y轴名称 | |
| 444 | - boundaryGap: [0, '100%'], | |
| 445 | - max: 100, | |
| 446 | - axisLabel: { | |
| 447 | - show: true, | |
| 448 | - interval: 'auto', | |
| 449 | - formatter: '{value} %' | |
| 450 | - }, | |
| 451 | - // y轴名称样式 | |
| 452 | - nameTextStyle: { | |
| 453 | - fontWeight: 300, | |
| 454 | - fontSize: 15 | |
| 455 | - } | |
| 456 | - }; | |
| 457 | - this.table1Option.dataZoom = [{ | |
| 458 | - show: true, | |
| 459 | - start: this.charZoomStart, | |
| 460 | - end: this.charZoomEnd | |
| 461 | - }]; | |
| 462 | - this.myChart1 = echarts.init(document.getElementById('WorkThreadsLoad')); | |
| 463 | - this.myChart1.setOption(this.table1Option); | |
| 464 | - this.myChart1.on('dataZoom', function (event) { | |
| 465 | - if (event.batch) { | |
| 466 | - that.charZoomStart = event.batch[0].start; | |
| 467 | - that.charZoomEnd = event.batch[0].end; | |
| 468 | - } else { | |
| 469 | - that.charZoomStart = event.start; | |
| 470 | - that.charZoomEnd = event.end; | |
| 471 | - } | |
| 472 | - }); | |
| 473 | - }, | |
| 474 | - | |
| 475 | - getAllSession: function () { | |
| 476 | - this.allSessionData = []; | |
| 477 | - if (!!this.mediaServerChoose) { | |
| 478 | - this.$axios({ | |
| 479 | - method: 'get', | |
| 480 | - url: '/zlm/' + this.mediaServerChoose + '/index/api/getAllSession' | |
| 481 | - }).then((res)=> { | |
| 482 | - res.data.data.forEach(item => { | |
| 483 | - let data = { | |
| 484 | - peer_ip: item.peer_ip, | |
| 485 | - local_ip: item.local_ip, | |
| 486 | - typeid: item.typeid, | |
| 487 | - id: item.id | |
| 488 | - }; | |
| 489 | - this.allSessionData.push(data); | |
| 490 | - }); | |
| 491 | - }); | |
| 492 | - } | |
| 493 | - | |
| 494 | - }, | |
| 495 | - getServerConfig: function () { | |
| 496 | - if (!!this.mediaServerChoose) { | |
| 497 | - this.$axios({ | |
| 498 | - method: 'get', | |
| 499 | - url: '/zlm/' + this.mediaServerChoose + '/index/api/getServerConfig' | |
| 500 | - }).then((res)=> { | |
| 501 | - let info = res.data.data[0]; | |
| 502 | - let serverInfo = {} | |
| 503 | - for (let i = 0; i < Object.keys(info).length; i++) { | |
| 504 | - let key = Object.keys(info)[i]; | |
| 505 | - let group = key.substring(0, key.indexOf(".")) | |
| 506 | - let itemKey = key.substring(key.indexOf(".") + 1) | |
| 507 | - if (!serverInfo[group]) serverInfo[group] = {} | |
| 508 | - serverInfo[group][itemKey] = info[key] | |
| 509 | - } | |
| 510 | - | |
| 511 | - this.serverConfig = serverInfo; | |
| 512 | - this.visible = true; | |
| 513 | - }); | |
| 514 | - } | |
| 515 | - | |
| 516 | - }, | |
| 517 | - getWVPServerConfig: function () { | |
| 518 | - let that = this; | |
| 519 | - this.$axios({ | |
| 520 | - method: 'get', | |
| 521 | - url: '/api/server/config' | |
| 522 | - }).then(function (res) { | |
| 523 | - console.log(res) | |
| 524 | - that.wvpServerConfig = res.data.data; | |
| 525 | - that.wvpVisible = true; | |
| 526 | - }); | |
| 527 | - this.$axios({ | |
| 528 | - method: 'get', | |
| 529 | - url: '/api/server/version' | |
| 530 | - }).then(function (res) { | |
| 531 | - console.log(res) | |
| 532 | - that.wvpServerVersion = res.data.data; | |
| 533 | - that.wvpVisible = true; | |
| 534 | - }); | |
| 535 | - }, | |
| 536 | - reStartServer: function () { | |
| 537 | - let that = this; | |
| 538 | - if (!!!this.mediaServerChoose) { | |
| 539 | - this.$message({ | |
| 540 | - type: 'info', | |
| 541 | - message: '未选择节点' | |
| 542 | - }); | |
| 543 | - return; | |
| 544 | - } | |
| 545 | - | |
| 546 | - this.$confirm('此操作将重启媒体服务器, 是否继续?', '提示', { | |
| 547 | - confirmButtonText: '确定', | |
| 548 | - cancelButtonText: '取消', | |
| 549 | - type: 'warning' | |
| 550 | - }).then(() => { | |
| 551 | - let that = this; | |
| 552 | - this.$axios({ | |
| 553 | - method: 'get', | |
| 554 | - url: '/zlm/' + that.mediaServerChoose + '/index/api/restartServer' | |
| 555 | - }).then(function (res) { | |
| 556 | - that.getAllSession(); | |
| 557 | - if (res.data.code === 0) { | |
| 558 | - that.$message({ | |
| 559 | - type: 'success', | |
| 560 | - message: '操作完成' | |
| 561 | - }); | |
| 562 | - } | |
| 563 | - }); | |
| 564 | - }); | |
| 565 | - }, | |
| 566 | - deleteRow: function (index, tabledata) { | |
| 567 | - let that = this; | |
| 568 | - this.$confirm('此操作将断开该通信链路, 是否继续?', '提示', { | |
| 569 | - confirmButtonText: '确定', | |
| 570 | - cancelButtonText: '取消', | |
| 571 | - type: 'warning' | |
| 572 | - }) | |
| 573 | - .then(() => { | |
| 574 | - that.deleteSession(tabledata[index].id); | |
| 575 | - }) | |
| 576 | - .catch(() => { | |
| 577 | - console.log('id:' + JSON.stringify(tabledata[index])); | |
| 578 | - this.$message({ | |
| 579 | - type: 'info', | |
| 580 | - message: '已取消删除' | |
| 581 | - }); | |
| 582 | - }); | |
| 583 | - console.log(JSON.stringify(tabledata[index])); | |
| 584 | - }, | |
| 585 | - deleteSession: function (id) { | |
| 586 | - if (!!this.mediaServerChoose) { | |
| 587 | - this.$axios({ | |
| 588 | - method: 'get', | |
| 589 | - url: '/zlm/' + this.mediaServerChoose + '/index/api/kick_session?id=' + id | |
| 590 | - }).then((res)=>{ | |
| 591 | - this.getAllSession(); | |
| 592 | - this.$message({ | |
| 593 | - type: 'success', | |
| 594 | - message: '删除成功!' | |
| 595 | - }); | |
| 596 | - }); | |
| 597 | - } | |
| 598 | - | |
| 599 | - }, | |
| 600 | - getNameFromKey: function (key) { | |
| 601 | - let nameData = { | |
| 602 | - "waitTrack": "等待编码信息", | |
| 603 | - "interfaceAuthenticationExcludes": "不进行鉴权的接口", | |
| 604 | - "playTimeout": "点播超时时间", | |
| 605 | - "autoApplyPlay": "自动点播", | |
| 606 | - "recordPushLive": "推流录像", | |
| 607 | - "redisConfig": "自动配置redis", | |
| 608 | - "thirdPartyGBIdReg": "stream信息正则", | |
| 609 | - "savePositionHistory": "保存轨迹信息", | |
| 610 | - "interfaceAuthentication": "接口鉴权", | |
| 611 | - "serverId": "服务ID", | |
| 612 | - "logInDatebase": "日志存储进数据库", | |
| 613 | - "seniorSdp": "扩展SDP", | |
| 614 | - "password": "密码", | |
| 615 | - "port": "端口号", | |
| 616 | - "keepaliveTimeOut": "心跳超时", | |
| 617 | - "domain": "国标域", | |
| 618 | - "ip": "IP地址", | |
| 619 | - "monitorIp": "监听IP", | |
| 620 | - "alarm": "存储报警信息", | |
| 621 | - "ptzSpeed": "云台控制速度", | |
| 622 | - "id": "国标ID", | |
| 623 | - "registerTimeInterval": "注册间隔", | |
| 624 | - "artifactId": "模块名称", | |
| 625 | - "version": "版本", | |
| 626 | - "project": "工程", | |
| 627 | - "git_Revision": "GIT修订版本", | |
| 628 | - "git_BRANCH": "GIT分支", | |
| 629 | - "git_URL": "GIT地址", | |
| 630 | - "build_DATE": "构建时间", | |
| 631 | - "create_By": "作者", | |
| 632 | - "git_Revision_SHORT": "GIT修订版本(短)", | |
| 633 | - "build_Jdk": "构建用JDK", | |
| 634 | - }; | |
| 635 | - console.log(key + ": " + nameData[key]) | |
| 636 | - | |
| 637 | - if (nameData[key]) { | |
| 638 | - return nameData[key] | |
| 639 | - } else { | |
| 640 | - return key; | |
| 641 | - } | |
| 642 | - }, | |
| 643 | - getMediaKeyNameFromKey: function (key) { | |
| 644 | - let nameData = { | |
| 645 | - "waitTrack": "等待编码信息", | |
| 646 | - "interfaceAuthenticationExcludes": "不进行鉴权的接口", | |
| 647 | - "playTimeout": "点播超时时间", | |
| 648 | - "autoApplyPlay": "自动点播", | |
| 649 | - "recordPushLive": "推流录像", | |
| 650 | - "redisConfig": "自动配置redis", | |
| 651 | - "thirdPartyGBIdReg": "stream信息正则", | |
| 652 | - "savePositionHistory": "保存轨迹信息", | |
| 653 | - "interfaceAuthentication": "接口鉴权", | |
| 654 | - "serverId": "服务ID", | |
| 655 | - "logInDatebase": "日志存储进数据库", | |
| 656 | - "seniorSdp": "扩展SDP", | |
| 657 | - "password": "密码", | |
| 658 | - "port": "端口号", | |
| 659 | - "keepaliveTimeOut": "心跳超时", | |
| 660 | - "domain": "国标域", | |
| 661 | - "ip": "IP地址", | |
| 662 | - "monitorIp": "监听IP", | |
| 663 | - "alarm": "存储报警信息", | |
| 664 | - "ptzSpeed": "云台控制速度", | |
| 665 | - "id": "国标ID", | |
| 666 | - "registerTimeInterval": "注册间隔", | |
| 667 | - "artifactId": "模块名称", | |
| 668 | - "version": "版本", | |
| 669 | - "project": "工程", | |
| 670 | - "git_Revision": "GIT修订版本", | |
| 671 | - "git_BRANCH": "GIT分支", | |
| 672 | - "git_URL": "GIT地址", | |
| 673 | - "build_DATE": "构建时间", | |
| 674 | - "create_By": "作者", | |
| 675 | - "git_Revision_SHORT": "GIT修订版本(短)", | |
| 676 | - "build_Jdk": "构建用JDK", | |
| 677 | - }; | |
| 678 | - console.log(key + ": " + nameData[key]) | |
| 679 | - | |
| 680 | - if (nameData[key]) { | |
| 681 | - return nameData[key] | |
| 682 | - } else { | |
| 683 | - return key; | |
| 684 | - } | |
| 685 | - } | |
| 686 | - } | |
| 687 | -}; | |
| 688 | -</script> | |
| 689 | - | |
| 690 | -<style> | |
| 691 | -#app { | |
| 692 | - height: 100%; | |
| 693 | -} | |
| 694 | - | |
| 695 | -.control-table { | |
| 696 | - background-color: #ffffff; | |
| 697 | - height: 25rem; | |
| 698 | -} | |
| 699 | - | |
| 700 | -.table-c { | |
| 701 | - border-right: 1px solid #dcdcdc; | |
| 702 | - border-bottom: 1px solid #dcdcdc; | |
| 703 | -} | |
| 704 | - | |
| 705 | -.table-c td { | |
| 706 | - border-left: 1px solid #dcdcdc; | |
| 707 | - border-top: 1px solid #dcdcdc; | |
| 708 | - padding: 0.2rem; | |
| 709 | -} | |
| 710 | - | |
| 711 | -.el-table { | |
| 712 | - width: 99.9% !important; | |
| 713 | -} | |
| 714 | -</style> |
web_src/src/main.js
| ... | ... | @@ -7,6 +7,7 @@ import router from './router/index.js'; |
| 7 | 7 | import axios from 'axios'; |
| 8 | 8 | import VueCookies from 'vue-cookies'; |
| 9 | 9 | import echarts from 'echarts'; |
| 10 | +import VCharts from 'v-charts'; | |
| 10 | 11 | |
| 11 | 12 | import VueClipboard from 'vue-clipboard2'; |
| 12 | 13 | import { Notification } from 'element-ui'; |
| ... | ... | @@ -39,6 +40,7 @@ Vue.use(VueClipboards); |
| 39 | 40 | Vue.prototype.$axios = axios; |
| 40 | 41 | Vue.prototype.$notify = Notification; |
| 41 | 42 | Vue.use(Contextmenu); |
| 43 | +Vue.use(VCharts); | |
| 42 | 44 | |
| 43 | 45 | axios.defaults.baseURL = (process.env.NODE_ENV === 'development') ? process.env.BASE_API : ""; |
| 44 | 46 | ... | ... |
web_src/src/router/index.js
| ... | ... | @@ -2,7 +2,7 @@ import Vue from 'vue' |
| 2 | 2 | import VueRouter from 'vue-router' |
| 3 | 3 | import Layout from "../layout/index.vue" |
| 4 | 4 | |
| 5 | -import control from '../components/control.vue' | |
| 5 | +import console from '../components/console.vue' | |
| 6 | 6 | import deviceList from '../components/DeviceList.vue' |
| 7 | 7 | import channelList from '../components/channelList.vue' |
| 8 | 8 | import pushVideoList from '../components/PushVideoList.vue' |
| ... | ... | @@ -37,11 +37,11 @@ export default new VueRouter({ |
| 37 | 37 | path: '/', |
| 38 | 38 | name: 'home', |
| 39 | 39 | component: Layout, |
| 40 | - redirect: '/control', | |
| 40 | + redirect: '/console', | |
| 41 | 41 | children: [ |
| 42 | 42 | { |
| 43 | - path: '/control', | |
| 44 | - component: control, | |
| 43 | + path: '/console', | |
| 44 | + component: console, | |
| 45 | 45 | }, |
| 46 | 46 | { |
| 47 | 47 | path: '/live', | ... | ... |