Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4c315a1548 | ||
|
|
4dfe872c27 | ||
|
|
d2e6e52fd0 | ||
|
|
df7dacdc39 | ||
|
|
0b54c730d7 | ||
|
|
70ddcb56ba | ||
|
|
719a08d993 | ||
|
|
81f287e9ff | ||
|
|
cf724e8693 | ||
|
|
869e2b23fb | ||
|
|
5d33611ef1 | ||
|
|
95c3001f35 | ||
|
|
6597b20ff9 | ||
|
|
25538b2cc4 | ||
|
|
14590545f5 | ||
|
|
f7a9258473 | ||
|
|
49b78d9933 | ||
|
|
b7fa412733 | ||
|
|
14864cbf9b | ||
|
|
c40942694e | ||
|
|
c1df7e2700 | ||
|
|
f6c3d730af | ||
|
|
22cab89749 | ||
|
|
c85b588719 | ||
|
|
2ac730dfe2 | ||
|
|
669bdf5b7d | ||
|
|
744867243f | ||
|
|
79830b752a | ||
|
|
4bb5a99b37 | ||
|
|
dfa8539b9b | ||
|
|
226a104417 | ||
|
|
539ecbc039 | ||
|
|
61adb5c8ae | ||
|
|
be2595f49d | ||
|
|
63d02ab19d | ||
|
|
12d2c50248 | ||
|
|
2bdad2db47 | ||
|
|
33055d74ba | ||
|
|
702eeb9caa | ||
|
|
8d01eb48e6 | ||
|
|
b98f2394b8 | ||
|
|
80f72549a2 | ||
|
|
bd729b7437 | ||
|
|
3aaa90746b | ||
|
|
b55b4ad49d | ||
|
|
ae171a2a82 | ||
|
|
2828deaece | ||
|
|
f8376c803f | ||
|
|
fe13f56aa1 | ||
|
|
1e27a414db | ||
|
|
6edd445e3d | ||
|
|
4a5008f1b5 | ||
|
|
749e880aa7 | ||
|
|
f0789acf42 | ||
|
|
5acbec4c45 | ||
|
|
4f6ad8edc4 | ||
|
|
4048d2b736 | ||
|
|
f919d31232 | ||
|
|
5e2184945c | ||
|
|
c3e046d9d9 | ||
|
|
33dc7cb7dc | ||
|
|
5cbe885d7e | ||
|
|
6b45194c65 | ||
|
|
1d3ab0f6af | ||
|
|
2d29bd4226 | ||
|
|
6bbd5d723e | ||
|
|
2a45acad33 | ||
|
|
c7dd92d3b3 | ||
|
|
905d8c3bb2 | ||
|
|
bb6cae1433 | ||
|
|
d85889b376 | ||
|
|
d1a20296d9 | ||
|
|
2f8c80572b | ||
|
|
7ef9d23e94 | ||
|
|
0a130781d1 | ||
|
|
6ce5a24614 | ||
|
|
627f847d5e | ||
|
|
89c2a61737 | ||
|
|
4403b06416 | ||
|
|
55f3e1c673 | ||
|
|
007b640209 | ||
|
|
59af80fe7f | ||
|
|
ed3b5bb5e8 | ||
|
|
58f78432f0 | ||
|
|
a2a5e52576 | ||
|
|
b50c962201 | ||
|
|
2209a7206f | ||
|
|
828c640307 | ||
|
|
4293c611be | ||
|
|
f155a0dc8e | ||
|
|
dbf6dfbe26 | ||
|
|
826e63a861 | ||
|
|
357292d445 | ||
|
|
87e5261942 | ||
|
|
5d60156456 | ||
|
|
ccd5edb76f | ||
|
|
99f7ddb760 | ||
|
|
40137f182c | ||
|
|
4666a0e9b3 | ||
|
|
17650d134a | ||
|
|
f40107a50f | ||
|
|
656dad2f3e | ||
|
|
c2dac86db0 | ||
|
|
858e3e6559 | ||
|
|
86cb6e0ffe | ||
|
|
3c485dea48 | ||
|
|
9b79fe8271 | ||
|
|
4f854f77b7 | ||
|
|
2191db06d4 | ||
|
|
274353d016 | ||
|
|
f0e63da1a2 | ||
|
|
4b34db817e | ||
|
|
a4aeb06d13 | ||
|
|
3389fbad53 | ||
|
|
3aa6822a72 | ||
|
|
bdfad20dd5 | ||
|
|
d8c9bbc775 | ||
|
|
5e014309cc | ||
|
|
390b9cf73e | ||
|
|
760beb0087 | ||
|
|
5b2f883934 | ||
|
|
98521a3a89 | ||
|
|
51c9f7fca3 | ||
|
|
d593abf718 | ||
|
|
fdd390c389 | ||
|
|
cfba4ecdb2 | ||
|
|
e45c17c4c5 | ||
|
|
f58a0151fe | ||
|
|
ff9aca14b8 | ||
|
|
de74af4fec | ||
|
|
393a90a0d0 | ||
|
|
3f06ab62b1 | ||
|
|
a148dc82a9 | ||
|
|
a039fd7a3a | ||
|
|
00485a5c7f | ||
|
|
50cf5e70fb | ||
|
|
7e5864b97b | ||
|
|
194ad023bd | ||
|
|
f16b07a2d6 | ||
|
|
7bf8bad9e4 | ||
|
|
ab1725e673 | ||
|
|
77631de0ff | ||
|
|
f6bdecd877 | ||
|
|
e05084afdc | ||
|
|
4c49640763 | ||
|
|
4433990878 | ||
|
|
6d092cb3e7 | ||
|
|
66957520f7 | ||
|
|
3596d7815b | ||
|
|
b72724649e | ||
|
|
aed81672a2 | ||
|
|
a1c530640c | ||
|
|
bcd7599676 | ||
|
|
5edb5932b5 | ||
|
|
7bd524976a | ||
|
|
7b7907616f | ||
|
|
e763418e38 | ||
|
|
36e4f2d5f1 | ||
|
|
38f0b9b560 | ||
|
|
246bb9a7e0 | ||
|
|
678bfce993 | ||
|
|
f8bc9fc622 | ||
|
|
d37fd4deae | ||
|
|
394cef66c2 | ||
|
|
7432f1e237 | ||
|
|
8eea52c4e5 | ||
|
|
4c777245fc | ||
|
|
42464bc5bd | ||
|
|
a436efab67 | ||
|
|
5ae056cb03 | ||
|
|
e37a7fb42b | ||
|
|
e3306bab3a | ||
|
|
2cdbcd6de8 | ||
|
|
fae66a2b79 | ||
|
|
f45ad79015 | ||
|
|
f9dd0964d2 | ||
|
|
30ca7ae14d | ||
|
|
82cb796a50 | ||
|
|
a98aeda96f | ||
|
|
1a10a5a9d1 | ||
|
|
edd3865094 | ||
|
|
8990fa8dee | ||
|
|
2b624b3c04 | ||
|
|
93b600affb | ||
|
|
bea6f032ac | ||
|
|
20b8531dc8 | ||
|
|
05c1638984 | ||
|
|
218dfef16b | ||
|
|
bcdb64777a | ||
|
|
dd9df3a08c | ||
|
|
fa12a5d3a8 | ||
|
|
0196b322f0 | ||
|
|
87cfc2ed79 | ||
|
|
b9bcd4c265 | ||
|
|
a54de8a9bb | ||
|
|
c5d7026fc5 | ||
|
|
93841a02ea | ||
|
|
42bd112649 | ||
|
|
d0add206ba | ||
|
|
b9659837c2 | ||
|
|
04f81af6c3 | ||
|
|
8bd1ea4faa | ||
|
|
fa00b6bfa8 | ||
|
|
6a8e08a81a | ||
|
|
25a33678f2 | ||
|
|
1e8081e83e | ||
|
|
88aea40885 | ||
|
|
a341800efc | ||
|
|
d75a2a1651 | ||
|
|
38c0e3d08d | ||
|
|
951d48f470 | ||
|
|
5f81d73c95 | ||
|
|
9ee5fef458 | ||
|
|
1723d314c5 | ||
|
|
f14316256c | ||
|
|
a945e4dc5f | ||
|
|
8575d5d711 | ||
|
|
a9cb35ba4f | ||
|
|
7e21e25cf3 | ||
|
|
ce9b8815df | ||
|
|
f2018eca30 | ||
|
|
af513ba157 | ||
|
|
1aa1b471a5 | ||
|
|
f42b921a50 | ||
|
|
db26e9a054 | ||
|
|
1dd2ae6a4c | ||
|
|
2d672250fd | ||
|
|
59f959fcc2 | ||
|
|
d35179c8ae | ||
|
|
9e0f6d3946 | ||
|
|
b627b6aa83 | ||
|
|
e98c6cda51 | ||
|
|
481b099655 | ||
|
|
d9534b635e | ||
|
|
d7173ff737 | ||
|
|
571bc840ad | ||
|
|
8664e72189 | ||
|
|
f1aec581c7 | ||
|
|
2492c7562a | ||
|
|
83690f95d7 | ||
|
|
02b071f4a0 | ||
|
|
beca94906c | ||
|
|
d6c10050b4 | ||
|
|
5fc9aa7c2f | ||
|
|
9214474325 | ||
|
|
55008a112c | ||
|
|
600ee94ed9 | ||
|
|
55f5734d7b | ||
|
|
a4fa53556b | ||
|
|
ca8f16fb0c | ||
|
|
6d7cde6058 | ||
|
|
2b8e222f23 | ||
|
|
00e97feac7 | ||
|
|
10dd1270fc | ||
|
|
94181fa0da | ||
|
|
9203113c09 | ||
|
|
e326bd1ef8 | ||
|
|
69bae32c80 | ||
|
|
00c20df133 | ||
|
|
bcb94ae9e7 | ||
|
|
64072af7ad | ||
|
|
b9f540f1ee | ||
|
|
cb7e3038fa | ||
|
|
460a4e1b3b | ||
|
|
14495fce2b | ||
|
|
e06b7d4fd3 | ||
|
|
72bd9004cc | ||
|
|
84b0ab50f4 | ||
|
|
aaaf5679ae | ||
|
|
b1bfb7a915 | ||
|
|
58919ad4d4 | ||
|
|
49f0037145 | ||
|
|
d0b5ee7e75 | ||
|
|
c37552661c | ||
|
|
d6a7d8348e | ||
|
|
586003c9b9 | ||
|
|
163ce9b64c | ||
|
|
1d5268d348 | ||
|
|
ef098b5d02 | ||
|
|
1eabb4445e | ||
|
|
b10aed3d14 | ||
|
|
6590a0c811 | ||
|
|
8eed156143 | ||
|
|
0ab9a98ba9 | ||
|
|
72dadaf3f2 | ||
|
|
f0079d67fd | ||
|
|
bc4560b8d9 | ||
|
|
466e56b90f | ||
|
|
aa0397ad1a | ||
|
|
c91f3e7927 | ||
|
|
69cf72af22 | ||
|
|
f3491a1a31 | ||
|
|
71ef748af8 | ||
|
|
5caa285ede | ||
|
|
e14c1ce771 | ||
|
|
8d22ab850a | ||
|
|
82af22b997 | ||
|
|
37a1f748e7 | ||
|
|
a24122ecd7 | ||
|
|
ccbea1fc51 | ||
|
|
ac7079b91a | ||
|
|
91c9829d77 | ||
|
|
5304b298f6 | ||
|
|
e09369aa5a | ||
|
|
3363e36669 | ||
|
|
ea2ce56e52 | ||
|
|
dee60e0699 | ||
|
|
8af7031c92 | ||
|
|
e62fc0c039 | ||
|
|
ad31a52663 | ||
|
|
de16b96971 | ||
|
|
ed9bff5d61 | ||
|
|
f0e34726ec | ||
|
|
3ca8154279 | ||
|
|
2cbd2e0aa7 | ||
|
|
73d7d64225 | ||
|
|
16913aa721 | ||
|
|
ba426d7737 | ||
|
|
3d4d785f33 | ||
|
|
8df5e278c8 | ||
|
|
ea8fb7cad2 | ||
|
|
b7b8b11860 | ||
|
|
1d02b17c20 | ||
|
|
bae61108be | ||
|
|
f60e530636 | ||
|
|
b3e9761305 | ||
|
|
5f75197a42 | ||
|
|
fbd2867ad2 | ||
|
|
2ca23ad99a | ||
|
|
4b032d74be | ||
|
|
8bfa73a67a | ||
|
|
f188e193f3 | ||
|
|
b362855a60 | ||
|
|
4c28d6b98c | ||
|
|
2276f2281a | ||
|
|
7ccb580e91 | ||
|
|
0346dfd584 | ||
|
|
5a64afe209 | ||
|
|
fd82d710b6 | ||
|
|
2056d7c51b | ||
|
|
91866293bc | ||
|
|
2714537140 | ||
|
|
fbc1535015 | ||
|
|
36de89570f | ||
|
|
22e595131c | ||
|
|
c037660b01 | ||
|
|
208d14d65a | ||
|
|
80b9cd83fb | ||
|
|
721ec4a5da | ||
|
|
fb9db32da7 | ||
|
|
874720b68d | ||
|
|
34f558199a | ||
|
|
597883fa08 | ||
|
|
07eab9378a | ||
|
|
806cbbd9ed | ||
|
|
8adf2a3dd0 | ||
|
|
2164ffc9b2 | ||
|
|
73a1a4c51b | ||
|
|
7091f1ffa6 | ||
|
|
fa44f6abe0 | ||
|
|
8586d7f1ce | ||
|
|
b2d818fc30 | ||
|
|
a20d5ee99f | ||
|
|
74b55423d5 | ||
|
|
7962c7e7a8 | ||
|
|
96acbc0919 | ||
|
|
6f5759b5ba | ||
|
|
322b5f18ed | ||
|
|
a7df09d56f | ||
|
|
e36dac9b81 | ||
|
|
8214175890 | ||
|
|
bc8207d29d | ||
|
|
9e55768312 | ||
|
|
6bfd0f4792 | ||
|
|
98ed8adfe3 | ||
|
|
f5938110f4 | ||
|
|
93e00ed436 | ||
|
|
acd8a33b4a | ||
|
|
33bdbd6d08 | ||
|
|
7ab2b3b546 | ||
|
|
b490e4f5b9 | ||
|
|
fe82336937 | ||
|
|
35a7ed5b35 | ||
|
|
56def56b58 | ||
|
|
6074078f5d | ||
|
|
428adb5186 | ||
|
|
1cbce9ad03 | ||
|
|
2138896d43 | ||
|
|
c40ee9c8cc | ||
|
|
d33183ca5e | ||
|
|
9ff9529402 | ||
|
|
51a8d6d3a0 | ||
|
|
c22663505c | ||
|
|
efa30f4ee3 | ||
|
|
9b589a0e69 | ||
|
|
401a7d65a0 | ||
|
|
91242e74b0 | ||
|
|
b0b9c69ad2 | ||
|
|
f8f2ba1f92 | ||
|
|
e3792eff57 | ||
|
|
5a3fa2a6ba | ||
|
|
081c79b85b | ||
|
|
5c0909e356 | ||
|
|
c1fdb68d96 | ||
|
|
b7da976819 | ||
|
|
41e37766b7 | ||
|
|
44612081bc | ||
|
|
4929ed30bc | ||
|
|
8f1de1c396 | ||
|
|
9b84ff9452 | ||
|
|
e4222e7b03 | ||
|
|
eea4e0069d | ||
|
|
2b69b8d72b | ||
|
|
1f130098ee | ||
|
|
5a4ab62e97 | ||
|
|
c86c498ab9 | ||
|
|
139a14fd3d | ||
|
|
6e7402fd63 | ||
|
|
2e91ab319f | ||
|
|
d537f56b9d | ||
|
|
7c4710e2e7 | ||
|
|
ea368f9162 | ||
|
|
7cab3f6556 | ||
|
|
a53eaaf533 | ||
|
|
302ea84cde | ||
|
|
7d470fd681 | ||
|
|
b64c4c66ab | ||
|
|
15ac549532 | ||
|
|
9bff669769 | ||
|
|
8a53ac8b9f | ||
|
|
d3a18f95db | ||
|
|
11649c3fb1 | ||
|
|
09fd8bc4dc | ||
|
|
5a704146a5 | ||
|
|
e25cd91df1 | ||
|
|
71f2e596fe | ||
|
|
7e60f0dd05 | ||
|
|
a0cc882a4b | ||
|
|
a94f9414a4 | ||
|
|
7f69bc69bc | ||
|
|
4b1058cff3 | ||
|
|
a6bab3fa0b | ||
|
|
d6c0f89de5 | ||
|
|
f3ae3da2a5 | ||
|
|
c44fae8d13 | ||
|
|
bcb214448c | ||
|
|
d5c91e733b | ||
|
|
ea6dfa7558 | ||
|
|
6129002b38 | ||
|
|
65db17a319 | ||
|
|
6969669027 | ||
|
|
38a698f07b | ||
|
|
9f121505d1 | ||
|
|
e11cb11ec9 | ||
|
|
6add41254d | ||
|
|
85bc4aea53 | ||
|
|
a95a96dfc0 | ||
|
|
9167da1bc5 | ||
|
|
5be94b499d | ||
|
|
69dfc2a1f5 | ||
|
|
b1a699252b | ||
|
|
f66454256b | ||
|
|
a0886abd38 | ||
|
|
9383c17484 | ||
|
|
512bd6d8eb | ||
|
|
b8b66fe610 | ||
|
|
154569304c | ||
|
|
cc3432ca06 | ||
|
|
68b9c5fa5e | ||
|
|
6620ac7279 | ||
|
|
a9a094d04a | ||
|
|
5d4a04ecf2 | ||
|
|
1b28260680 | ||
|
|
83cb3f8728 | ||
|
|
7d69d3c21d | ||
|
|
ebde50f58b | ||
|
|
b8924d161f | ||
|
|
ccb52ea94f | ||
|
|
72abbe1c53 | ||
|
|
f318f61b4a | ||
|
|
45d8314e29 | ||
|
|
886a1c8667 | ||
|
|
378729720d | ||
|
|
c2a3d4b8a8 | ||
|
|
8444de8e98 | ||
|
|
874e01996a | ||
|
|
fb855fd74e | ||
|
|
78f963fbea | ||
|
|
cf0116b5c6 | ||
|
|
80b07c462f | ||
|
|
5a8ab1343f | ||
|
|
67349e24d8 | ||
|
|
f59697a2f2 | ||
|
|
8c197bee04 | ||
|
|
f866fbf153 | ||
|
|
d7b4fd3f71 | ||
|
|
1c07167f1a | ||
|
|
d5c42f761e | ||
|
|
29449cc597 | ||
|
|
7615bccf04 | ||
|
|
831e7ee987 | ||
|
|
f5f27d78f1 | ||
|
|
ebc46ff7d4 | ||
|
|
2513baf48e | ||
|
|
ac2483d690 | ||
|
|
a85f87f3fc | ||
|
|
68e002776c | ||
|
|
9322f52c9a | ||
|
|
f15e52573b | ||
|
|
2c9807f9b8 | ||
|
|
fcf32800fe | ||
|
|
f8f4dc0f2e | ||
|
|
49bd59c639 | ||
|
|
a96c587559 | ||
|
|
6bd7a28458 | ||
|
|
053517324d | ||
|
|
256802e698 | ||
|
|
851e8a461e | ||
|
|
d8d49f23c4 | ||
|
|
1511792e3b | ||
|
|
0544495d70 | ||
|
|
045a25f3ae | ||
|
|
b6d1ba6766 | ||
|
|
e8e0e07189 | ||
|
|
1672c6c6ba | ||
|
|
ac251c2c00 | ||
|
|
5d7334a4de | ||
|
|
9b9c0b39fd | ||
|
|
802a91a96d | ||
|
|
31bca2b98f | ||
|
|
bf94591035 | ||
|
|
d523b60311 | ||
|
|
e0990a40df | ||
|
|
20c1c455c4 | ||
|
|
dab76add73 | ||
|
|
101cb70893 | ||
|
|
348b11e201 | ||
|
|
a9fdda3f5e | ||
|
|
89d22e55c7 | ||
|
|
40f2a78717 | ||
|
|
80ee1c05ff | ||
|
|
021f9f28f6 | ||
|
|
d7990a6ee5 | ||
|
|
3561a5dc39 | ||
|
|
247a009eef | ||
|
|
fcd4db8217 | ||
|
|
3e03d47520 | ||
|
|
414afea783 | ||
|
|
df7c455881 | ||
|
|
1644765ce2 | ||
|
|
db16cdb79b | ||
|
|
800547d1ef | ||
|
|
5614be7877 | ||
|
|
0644e49161 | ||
|
|
44cd1d354a | ||
|
|
15b81eef97 | ||
|
|
5ddf83d1fd | ||
|
|
6326f46bf2 | ||
|
|
f75719ca37 | ||
|
|
21cf86baff | ||
|
|
6583bc9972 | ||
|
|
886ea37702 | ||
|
|
23116db988 | ||
|
|
8283523327 | ||
|
|
33159befc3 | ||
|
|
c567b19fb2 | ||
|
|
d8487d7cd7 | ||
|
|
347c9f1d3b | ||
|
|
a731a6408b | ||
|
|
c0ac1f6ed5 | ||
|
|
544c3697bd | ||
|
|
33a8ce97d3 | ||
|
|
6ee9d464fb | ||
|
|
df5072bae7 | ||
|
|
ae94e3bf2a | ||
|
|
2276445ff6 | ||
|
|
e12dce1f0f | ||
|
|
612592ec2a | ||
|
|
d0457fc285 | ||
|
|
e04fd4077e | ||
|
|
63d32f0a39 | ||
|
|
99565dd652 | ||
|
|
2b9fa490d4 | ||
|
|
7e03437ab6 | ||
|
|
5f9d19ac65 | ||
|
|
f23d4117d7 | ||
|
|
e4a56d68e0 | ||
|
|
cf5d08aaab | ||
|
|
7ad566d74f | ||
|
|
c312186d91 | ||
|
|
e3f7b08c69 | ||
|
|
6e3ef7e56a | ||
|
|
0a96fee6c3 | ||
|
|
dc7d24e2bf | ||
|
|
089ae12dd1 | ||
|
|
da0d49d306 | ||
|
|
670225a655 | ||
|
|
fa35bfc340 | ||
|
|
f4a5d28a29 | ||
|
|
c735aeba6d | ||
|
|
3c058ec107 | ||
|
|
327e82e057 | ||
|
|
012fc44f08 | ||
|
|
0ab04ab819 | ||
|
|
580b931610 | ||
|
|
dd7df775e2 | ||
|
|
18c2a2e4dc | ||
|
|
fbdd04b4dd | ||
|
|
72fd372fe0 | ||
|
|
acdadcbb6f | ||
|
|
7a49de71ea | ||
|
|
56e4419e77 | ||
|
|
3abb4dd4bd | ||
|
|
726a284ab5 | ||
|
|
a45243390b | ||
|
|
1faed9bc3d | ||
|
|
9bd700eeb7 | ||
|
|
5cc3b9c8cf | ||
|
|
208895c7d5 | ||
|
|
46578ce97b | ||
|
|
0ff5bd5e20 | ||
|
|
f08e637e69 | ||
|
|
a600e056b8 | ||
|
|
671c80972e | ||
|
|
d07230b582 | ||
|
|
35c24407ac | ||
|
|
cf33756548 | ||
|
|
1ef98298bc | ||
|
|
b1c2a95ec4 | ||
|
|
147b2fad8d | ||
|
|
b629088406 | ||
|
|
b508d4393c | ||
|
|
430a067280 | ||
|
|
8a71e8f773 | ||
|
|
ff556ce1ec | ||
|
|
9ed7aed4b4 | ||
|
|
d257151718 | ||
|
|
9e14297488 | ||
|
|
8e70706ed5 | ||
|
|
3e0529cf87 | ||
|
|
91af2bed92 | ||
|
|
1ecefb91dc | ||
|
|
7b60c30548 | ||
|
|
cf5c8906c3 | ||
|
|
72d9895902 | ||
|
|
249c9a5a6e | ||
|
|
41fa214137 | ||
|
|
1565f25a03 | ||
|
|
c5c2926d99 | ||
|
|
a78b830a05 | ||
|
|
879cf783b6 | ||
|
|
895a55f367 | ||
|
|
536c77ff08 | ||
|
|
55456f9220 | ||
|
|
37e70e7af8 | ||
|
|
cf1686c348 | ||
|
|
f7833bcd9f | ||
|
|
5a621053a4 | ||
|
|
2a6451ef2a | ||
|
|
87e044276c | ||
|
|
f1b440c8dd | ||
|
|
cd3e87c1c9 | ||
|
|
a67e54ca6e | ||
|
|
53d9e63c36 | ||
|
|
009c4cf590 | ||
|
|
3c45427bff | ||
|
|
56cbe9915c | ||
|
|
cf3103db46 | ||
|
|
b4623d19e5 | ||
|
|
700bff6e38 | ||
|
|
d77c4e43d4 | ||
|
|
6e11d2b16a | ||
|
|
405842bc0b | ||
|
|
879499b595 | ||
|
|
bf8d7f2124 | ||
|
|
ba98b37306 | ||
|
|
aa8ed65fd8 | ||
|
|
936a4410b3 | ||
|
|
58ec76f9e5 | ||
|
|
c1a77c8e48 | ||
|
|
477e8e4631 | ||
|
|
4f9d65a3a7 | ||
|
|
e199498a8e | ||
|
|
b1799d8ccb | ||
|
|
86833e7d6b | ||
|
|
59cf57898b | ||
|
|
fb9382e3a0 | ||
|
|
dae4697cd2 | ||
|
|
1b2e892f74 | ||
|
|
c66c640f75 | ||
|
|
30849416b6 | ||
|
|
5edcee8da5 | ||
|
|
311beed2a7 | ||
|
|
eb5fdfb635 | ||
|
|
78bcde9ef2 | ||
|
|
630e2a16ad | ||
|
|
82ecee9941 | ||
|
|
e1fe031f25 | ||
|
|
855ba7dc9e | ||
|
|
3a72e73d5d | ||
|
|
4cb13a1419 | ||
|
|
8dd84a5255 | ||
|
|
c0e62f48b7 | ||
|
|
b992225e28 | ||
|
|
2f04562a34 | ||
|
|
4ee1d87d04 | ||
|
|
39268e2162 | ||
|
|
d6b755c234 | ||
|
|
a889f97bd6 | ||
|
|
a77b968a17 | ||
|
|
da3d712e97 | ||
|
|
bb662aefe3 | ||
|
|
7bbffccd21 | ||
|
|
d3a452cfd8 | ||
|
|
d81b8cdf38 | ||
|
|
39a417368a | ||
|
|
adfce5d2f7 | ||
|
|
977286d6b3 | ||
|
|
c33000045a | ||
|
|
b995ac378a | ||
|
|
0de115ad9e | ||
|
|
ec67414cb6 | ||
|
|
6bea64f345 | ||
|
|
94886e255e | ||
|
|
45f66afe52 | ||
|
|
b9105c1e77 | ||
|
|
909d306942 | ||
|
|
f7273457e9 | ||
|
|
c30e8b4891 | ||
|
|
2e5ad2f65d | ||
|
|
7d5d82e7fc | ||
|
|
776e9c5837 | ||
|
|
0d4979d3d9 | ||
|
|
686c7dd273 | ||
|
|
d41b308c6d | ||
|
|
84dac247d2 | ||
|
|
f8439bb40a | ||
|
|
d268d920e7 | ||
|
|
f730ef1e3a | ||
|
|
af1ce32063 | ||
|
|
678ff2d09d | ||
|
|
48f674b6ef | ||
|
|
02f0820a69 | ||
|
|
ca8605fd6e | ||
|
|
6d5e96421b | ||
|
|
bcc29007bf | ||
|
|
bdf904078d | ||
|
|
e37cfa5066 | ||
|
|
f1bff23bbc | ||
|
|
53106ddb5c | ||
|
|
3a04882fe5 | ||
|
|
19202a5e81 | ||
|
|
7b311ff673 | ||
|
|
9dba98e0ee | ||
|
|
71338670f0 | ||
|
|
7dcdfabce2 | ||
|
|
ddfe1723c9 | ||
|
|
57b5f76db7 | ||
|
|
9ac3524877 | ||
|
|
ca82a0a74b | ||
|
|
23007c3bf2 | ||
|
|
5d69d7612a | ||
|
|
ddd8930af4 | ||
|
|
757f2ec20a | ||
|
|
30caa79424 | ||
|
|
e3f83a0b98 | ||
|
|
147a3ed77b | ||
|
|
5d35d950b3 | ||
|
|
6874508d3f | ||
|
|
33f468209a | ||
|
|
e8ef2816df | ||
|
|
e38d7bbffa | ||
|
|
2f1265c47a | ||
|
|
66b6b60505 | ||
|
|
249d14320d | ||
|
|
313b90ad31 | ||
|
|
2ebc90e974 | ||
|
|
640257dd55 | ||
|
|
c1a3ce8068 | ||
|
|
0080e9c26e | ||
|
|
2ccafe622d | ||
|
|
d7a515ed9a | ||
|
|
cd82b71b77 | ||
|
|
9d6a7dcd9c | ||
|
|
46c2affcc8 | ||
|
|
3d00a80588 | ||
|
|
a3c1fe154f | ||
|
|
07dce5a27e | ||
|
|
60083183c5 | ||
|
|
255cf026a6 | ||
|
|
840ea56c42 | ||
|
|
09917cc9c9 | ||
|
|
4c9fe192f2 | ||
|
|
32ec55d44e | ||
|
|
527cf89d1a | ||
|
|
ac7b57c0ae | ||
|
|
8be1a8968e | ||
|
|
999ccf64ad | ||
|
|
8fbd4f3952 | ||
|
|
03352f3aa8 | ||
|
|
61a58fc661 | ||
|
|
4268fa3198 | ||
|
|
2048b6f2db | ||
|
|
f6b62c6c7e | ||
|
|
b4cbc1c190 | ||
|
|
1871f6f656 | ||
|
|
409f9836a6 | ||
|
|
b3f40ee683 | ||
|
|
aa07b51663 | ||
|
|
19b77ed005 | ||
|
|
ea6fca405b | ||
|
|
06503fd079 | ||
|
|
2321dacd2a | ||
|
|
a8b4e91b95 | ||
|
|
a5075bef43 | ||
|
|
f4ffbc1c86 | ||
|
|
6cafa284c7 | ||
|
|
049c0e7a0f | ||
|
|
377ffc6e10 | ||
|
|
858431e86e | ||
|
|
70fca5ca41 | ||
|
|
e972d14a9a | ||
|
|
9bc5eba0d6 | ||
|
|
b8c56c8868 | ||
|
|
9785837980 | ||
|
|
977a4e11ee | ||
|
|
21e42709a7 | ||
|
|
f8a43042db | ||
|
|
a9ee7aa925 | ||
|
|
811aedaaf4 | ||
|
|
172b4a4856 | ||
|
|
447ee401cb | ||
|
|
5f8e9954fe | ||
|
|
f8a234822d | ||
|
|
09245fdfda | ||
|
|
3dafe8d1f6 | ||
|
|
c7606df740 | ||
|
|
e5c40d11d3 | ||
|
|
c9d8bb87de | ||
|
|
f7c2adf58c | ||
|
|
363288a141 | ||
|
|
b1dbacffcc | ||
|
|
3089f8911e | ||
|
|
83ec17343a | ||
|
|
ef9db9ddf6 | ||
|
|
1e8da20c44 | ||
|
|
d9b2b6b567 | ||
|
|
636c7a5939 | ||
|
|
15f6cf0b4c | ||
|
|
c024c304d5 | ||
|
|
a6e100b5c2 | ||
|
|
48bac47c6b | ||
|
|
24a147afaf | ||
|
|
5b17c9e497 | ||
|
|
79f143c22c | ||
|
|
a8764fe627 | ||
|
|
6a0ed31cdc | ||
|
|
8a2e21a794 | ||
|
|
51226fbfb4 | ||
|
|
af5ac7d29a | ||
|
|
0b98a1f697 | ||
|
|
f66cd875fb | ||
|
|
795a6fabee | ||
|
|
1f7becef0a | ||
|
|
aa4f11bf44 | ||
|
|
0b6a08a977 | ||
|
|
5089e769da | ||
|
|
c36f402528 | ||
|
|
1f6a13951f | ||
|
|
4b69b44df5 | ||
|
|
5643c625ef | ||
|
|
1607c97b82 | ||
|
|
d0ac6d4e2e | ||
|
|
0ad9d546cd | ||
|
|
f8d54e35c9 | ||
|
|
be2a077bba | ||
|
|
cb5dfebb59 | ||
|
|
71d23cbc32 | ||
|
|
93315776da | ||
|
|
0d5cbe6459 | ||
|
|
9a88364d8b | ||
|
|
c0ec4893c8 | ||
|
|
24cd0ff101 | ||
|
|
7e92659217 | ||
|
|
e8fefab74e | ||
|
|
78c86be8a0 | ||
|
|
8f8c9f8395 | ||
|
|
7d5635560d | ||
|
|
e83bf43bc8 | ||
|
|
f89ba87fef | ||
|
|
ca8a4128fb | ||
|
|
21621c2056 | ||
|
|
22797a8ae8 | ||
|
|
374b6feef3 | ||
|
|
c1902f978a | ||
|
|
b431ae70a5 | ||
|
|
8e57bcfd25 | ||
|
|
9e5a000383 | ||
|
|
f4771892aa | ||
|
|
842f09cc90 | ||
|
|
2cb92eaf69 | ||
|
|
02eb368a45 | ||
|
|
4c7b5c8b55 | ||
|
|
7aebab3734 | ||
|
|
d26fb9af85 | ||
|
|
28213cde43 | ||
|
|
c21af696fe | ||
|
|
ebd8821e64 | ||
|
|
361fdf6959 | ||
|
|
60dc02010d | ||
|
|
7c420c7c95 | ||
|
|
a78e7049cf | ||
|
|
ef3796c34f | ||
|
|
c38855acf8 | ||
|
|
a2672d300f | ||
|
|
bfaf0e6aaf | ||
|
|
7fe0f5d84d | ||
|
|
1eeddb20c5 | ||
|
|
52b61ec34a | ||
|
|
faefef7d2f | ||
|
|
938679cbda | ||
|
|
83aefc5dde | ||
|
|
0157ec50d3 | ||
|
|
2f7c947708 | ||
|
|
4c16c39243 | ||
|
|
693ed533f9 | ||
|
|
584b25d9fc | ||
|
|
1fa59d163e | ||
|
|
c94f9c5943 | ||
|
|
2480ae1c0b | ||
|
|
440dc81182 | ||
|
|
0b64302b54 | ||
|
|
0e4e8e09e6 | ||
|
|
0b05f40e65 | ||
|
|
ff0b3a40cd | ||
|
|
fe541886d5 | ||
|
|
6406ed0e57 | ||
|
|
1aa2f2382a | ||
|
|
197a962c0d | ||
|
|
ac923d5943 | ||
|
|
92fe93b4dc | ||
|
|
a26301af1e | ||
|
|
6aa07dc756 | ||
|
|
f5faa054b3 | ||
|
|
5ada366f17 | ||
|
|
80a41dd559 | ||
|
|
7031d4cdd4 | ||
|
|
f72b79c628 | ||
|
|
490db476dd | ||
|
|
1bae6e55e0 | ||
|
|
d2503348fd | ||
|
|
03710d6811 | ||
|
|
322dccfbc1 | ||
|
|
0d0603058c | ||
|
|
acef786c56 | ||
|
|
4e726913f1 | ||
|
|
f699f6f3ba | ||
|
|
e35356a8c6 | ||
|
|
9152f14430 | ||
|
|
faa3fa546b | ||
|
|
5c31093c28 | ||
|
|
eee652bd1f | ||
|
|
b7b66ad28d | ||
|
|
29e092421c | ||
|
|
0022e259ca | ||
|
|
0a711ee3ce |
No files matched your search
@@ -1,5 +1,5 @@
|
|||||||
# 历史路径-哈希带井号标识
|
# 历史路径-哈希带井号标识
|
||||||
VITE_HISTORY_HASH = false
|
VITE_HISTORY_HASH = true
|
||||||
|
|
||||||
# 历史路径-前缀URL如:/h5
|
# 历史路径-前缀URL如:/h5
|
||||||
VITE_HISTORY_BASE_URL = "/"
|
VITE_HISTORY_BASE_URL = "/"
|
||||||
@@ -11,7 +11,7 @@ VITE_APP_NAME = "Core Network OMC"
|
|||||||
VITE_APP_CODE = "OMC"
|
VITE_APP_CODE = "OMC"
|
||||||
|
|
||||||
# 应用版本
|
# 应用版本
|
||||||
VITE_APP_VERSION = "2.241115"
|
VITE_APP_VERSION = "local-dev"
|
||||||
|
|
||||||
# 接口基础URL地址-不带/后缀
|
# 接口基础URL地址-不带/后缀
|
||||||
VITE_API_BASE_URL = "/omc-api"
|
VITE_API_BASE_URL = "/omc-api"
|
||||||
@@ -11,7 +11,7 @@ VITE_APP_NAME = "Core Network OMC"
|
|||||||
VITE_APP_CODE = "OMC"
|
VITE_APP_CODE = "OMC"
|
||||||
|
|
||||||
# 应用版本
|
# 应用版本
|
||||||
VITE_APP_VERSION = "2.241115"
|
VITE_APP_VERSION = "local-prod"
|
||||||
|
|
||||||
# 接口基础URL地址-不带/后缀
|
# 接口基础URL地址-不带/后缀
|
||||||
VITE_API_BASE_URL = "/omc-api"
|
VITE_API_BASE_URL = "/omc-api"
|
||||||
@@ -1,5 +1,43 @@
|
|||||||
# 版本发布日志
|
# 版本发布日志
|
||||||
|
|
||||||
|
## 2.2510.4-20251024
|
||||||
|
|
||||||
|
- 修复 AMF配置WhiteList Content导入index0无效问题
|
||||||
|
- 新增 更新背景图片固定BA的
|
||||||
|
- 新增 基站状态补充randId列
|
||||||
|
- 新增 Roaming CDR自定义导出功能
|
||||||
|
- 优化 基站名称和位置信息改为非必填
|
||||||
|
- 修复 网元信息更新响应修复
|
||||||
|
- 新增 UDM鉴权cnFlag添加5G/4G接入选择
|
||||||
|
- 新增 更新getAllNeConfig函数,支持传入neId参数
|
||||||
|
- 修复 更新根网管节点处理逻辑,支持无OMC情况
|
||||||
|
- 优化 移除ID列显示
|
||||||
|
- 优化 操作日志信息json结构格式美化
|
||||||
|
- 优化 备份网元日志文件数据查看
|
||||||
|
- 优化 悬浮标签修改
|
||||||
|
|
||||||
|
## 2.2510.2-20251011
|
||||||
|
|
||||||
|
- 新增 UDM-auth数据导出按钮权限定义
|
||||||
|
- 新增 SMSC-CDR添加结果原因说明
|
||||||
|
- 优化 移除CDR/UE/网元版本/授权列表显示ID列
|
||||||
|
- 修复 MML回车undefined问题,关闭搜索匹配
|
||||||
|
|
||||||
|
## 2.2408.1-20250815
|
||||||
|
|
||||||
|
- 修复 给config.js加随机数避免缓存
|
||||||
|
- 优化 UDM鉴权用户显示创建时间
|
||||||
|
- 修复 系统用户登录主页重复刷新问题
|
||||||
|
- 新增 kpi自定义仪表盘需求更改
|
||||||
|
- 修复 租户主页暗色模式显示不一致
|
||||||
|
- 修复 租户和系统用户的主页显示差异
|
||||||
|
- 修复 图片上传取值fileName失败
|
||||||
|
- 优化 第三方用户不可删除和修改密码
|
||||||
|
- 修复 恢复显示快速PLMN修改窗口
|
||||||
|
- 新增 第三方登录认证功能和管理页
|
||||||
|
- 修复 回退看板,修复切换upf的流量统计显示
|
||||||
|
|
||||||
|
|
||||||
## 2.2404.1-20240402
|
## 2.2404.1-20240402
|
||||||
|
|
||||||
- 新增 网元安装流程相关页面与操作相关接口联调
|
- 新增 网元安装流程相关页面与操作相关接口联调
|
||||||
|
|||||||
@@ -46,5 +46,31 @@ export NODE_OPTIONS=--max-old-space-size=50000
|
|||||||
|
|
||||||
```text
|
```text
|
||||||
https://192.168.5.23/
|
https://192.168.5.23/
|
||||||
admin / admin
|
admin
|
||||||
|
admin
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
## 多租户涉及页面
|
||||||
|
ems_frontend_vue3\src\views\dashboard\smfCDR\index.vue
|
||||||
|
ems_frontend_vue3\src\views\dashboard\imsCDR\index.vue
|
||||||
|
ems_frontend_vue3\src\views\dashboard\amfUE\index.vue
|
||||||
|
ems_frontend_vue3\src\views\dashboard\mmeUE\index.vue
|
||||||
|
ems_frontend_vue3\src\views\system\user\index.vue
|
||||||
|
ems_frontend_vue3\src\views\system\tenant\index.vue
|
||||||
|
ems_frontend_vue3\src\views\system\log\operate\index.vue
|
||||||
|
ems_frontend_vue3\src\views\neUser\sub\index.vue
|
||||||
|
ems_frontend_vue3\src\views\neUser\ims\index.vue
|
||||||
|
ems_frontend_vue3\src\views\neUser\ue\index.vue
|
||||||
|
ems_frontend_vue3\src\views\neUser\base5G\index.vue
|
||||||
|
|
||||||
|
ems_frontend_vue3\src\views\tenant\amfUE\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\base5G\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\ims\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\imsCDR\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\mmeUE\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\operate\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\smfCDR\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\sub\index.vue
|
||||||
|
ems_frontend_vue3\src\views\tenant\ue\index.vue
|
||||||
@@ -2,14 +2,18 @@
|
|||||||
<html lang="zh-CN">
|
<html lang="zh-CN">
|
||||||
<head>
|
<head>
|
||||||
<meta charset="UTF-8" />
|
<meta charset="UTF-8" />
|
||||||
<meta name="google" content="notranslate">
|
<meta name="google" content="notranslate" />
|
||||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||||
<title>loading...</title>
|
<title>loading...</title>
|
||||||
<link rel="icon" href="/favicon.ico" />
|
<link rel="icon" href="/favicon.ico" />
|
||||||
<link rel="preload" href="/loading.js" as="script">
|
<link rel="preload" href="/loading.js" as="script"/>
|
||||||
<script async src="/loading.js"></script>
|
<script async src="/loading.js"></script>
|
||||||
<link rel="preload" href="/config.js" as="script">
|
<script>
|
||||||
<script async src="/config.js"></script>
|
var script = document.createElement('script');
|
||||||
|
script.src = '/config.js?nocache=' + new Date().getTime();
|
||||||
|
script.async = true;
|
||||||
|
document.head.appendChild(script);
|
||||||
|
</script>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<div id="app"></div>
|
<div id="app"></div>
|
||||||
|
|||||||
@@ -8,54 +8,55 @@
|
|||||||
},
|
},
|
||||||
"scripts": {
|
"scripts": {
|
||||||
"dev": "vite",
|
"dev": "vite",
|
||||||
"build": "vue-tsc && vite build",
|
"build": "vite build",
|
||||||
"preview": "vite preview"
|
"preview": "vite preview"
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@ant-design/icons-vue": "^7.0.1",
|
"@ant-design/icons-vue": "7.0.1",
|
||||||
"@antv/g6": "~4.8.24",
|
"@antv/g6": "4.8.24",
|
||||||
"@codemirror/lang-javascript": "^6.2.2",
|
"@codemirror/lang-javascript": "6.2.3",
|
||||||
"@codemirror/lang-yaml": "^6.1.1",
|
"@codemirror/lang-yaml": "6.1.2",
|
||||||
"@codemirror/merge": "^6.7.2",
|
"@codemirror/merge": "6.10.0",
|
||||||
"@codemirror/theme-one-dark": "^6.1.2",
|
"@codemirror/theme-one-dark": "6.1.2",
|
||||||
"@tato30/vue-pdf": "^1.11.2",
|
"@tato30/vue-pdf": "1.11.3",
|
||||||
"@vueuse/core": "11.2.0",
|
"@vueuse/core": "13.0.0",
|
||||||
"@xterm/addon-fit": "^0.10.0",
|
"@xterm/addon-fit": "0.10.0",
|
||||||
"@xterm/xterm": "^5.5.0",
|
"@xterm/xterm": "5.5.0",
|
||||||
"ant-design-vue": "^4.2.5",
|
"ant-design-vue": "4.2.6",
|
||||||
"antdv-pro-layout": "^4.1.9",
|
"antdv-pro-layout": "4.2.0",
|
||||||
"antdv-pro-modal": "^4.0.5",
|
"antdv-pro-modal": "4.0.6",
|
||||||
"codemirror": "^6.0.1",
|
"codemirror": "6.0.1",
|
||||||
"crypto-js": "^4.2.0",
|
"crypto-js": "4.2.0",
|
||||||
"dayjs": "^1.11.11",
|
"dayjs": "1.11.13",
|
||||||
"echarts": "~5.5.0",
|
"echarts": "5.6.0",
|
||||||
"file-saver": "^2.0.5",
|
"echarts-liquidfill": "^3.1.0",
|
||||||
"grid-layout-plus": "^1.0.5",
|
"file-saver": "2.0.5",
|
||||||
"intl-tel-input": "^24.6.0",
|
"grid-layout-plus": "1.0.6",
|
||||||
|
"intl-tel-input": "25.2.0",
|
||||||
"js-base64": "^3.7.7",
|
"js-base64": "^3.7.7",
|
||||||
"js-cookie": "^3.0.5",
|
"js-cookie": "^3.0.5",
|
||||||
"localforage": "^1.10.0",
|
"localforage": "^1.10.0",
|
||||||
"nprogress": "^0.2.0",
|
"nprogress": "^0.2.0",
|
||||||
"p-queue": "~8.0.1",
|
"p-queue": "8.0.1",
|
||||||
"pinia": "2.2.6",
|
"pinia": "2.3.0",
|
||||||
"vue": "^3.5.12",
|
"vue": "3.5.13",
|
||||||
"vue-i18n": "^10.0.4",
|
"vue-i18n": "11.1.2",
|
||||||
"vue-router": "^4.4.5",
|
"vue-router": "4.5.0",
|
||||||
"vue3-smooth-dnd": "^0.0.6",
|
"vue3-smooth-dnd": "0.0.6",
|
||||||
"xlsx": "~0.18.5"
|
"xlsx": "0.18.5"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@types/crypto-js": "^4.2.2",
|
"@types/crypto-js": "4.2.2",
|
||||||
"@types/file-saver": "^2.0.7",
|
"@types/file-saver": "2.0.7",
|
||||||
"@types/js-cookie": "^3.0.6",
|
"@types/js-cookie": "3.0.6",
|
||||||
"@types/node": "^22.7.7",
|
"@types/node": "^18.0.0",
|
||||||
"@types/nprogress": "^0.2.3",
|
"@types/nprogress": "0.2.3",
|
||||||
"@vitejs/plugin-vue": "^5.1.4",
|
"@vitejs/plugin-vue": "5.2.3",
|
||||||
"less": "^4.2.0",
|
"less": "4.2.2",
|
||||||
"typescript": "^5.6.3",
|
"typescript": "5.8.2",
|
||||||
"unplugin-vue-components": "^0.27.4",
|
"unplugin-vue-components": "0.28.0",
|
||||||
"vite": "5.4.10",
|
"vite": "6.2.2",
|
||||||
"vite-plugin-compression": "~0.5.1",
|
"vite-plugin-compression": "0.5.1",
|
||||||
"vue-tsc": "^2.1.8"
|
"vue-tsc": "2.2.8"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
After Width: | Height: | Size: 217 KiB |
|
After Width: | Height: | Size: 217 KiB |
@@ -10,12 +10,19 @@
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
(function () {
|
(function () {
|
||||||
// host = ip:port
|
// baseUrl = protocol://ip:port
|
||||||
// const host = '192.168.8.100:33030';
|
// baseUrl = 'http://192.168.8.100:33030';
|
||||||
const host = `${window.location.hostname}:33030`;
|
const protocol = window.location.protocol
|
||||||
|
let wsprotocol = "ws:"
|
||||||
|
const hostname = window.location.hostname
|
||||||
|
let host = `${hostname}:33030`;
|
||||||
|
if (protocol === 'https:') {
|
||||||
|
host = `${hostname}:33443`;
|
||||||
|
wsprotocol = "wss:"
|
||||||
|
}
|
||||||
|
|
||||||
// Service Address
|
// Service Address
|
||||||
sessionStorage.setItem('baseUrl', `http://${host}`);
|
sessionStorage.setItem('baseUrl', `${protocol}//${host}`);
|
||||||
// websocket Address
|
// websocket Address
|
||||||
sessionStorage.setItem('wsUrl', `ws://${host}`);
|
sessionStorage.setItem('wsUrl', `${wsprotocol}//${host}`);
|
||||||
})();
|
})();
|
||||||
@@ -0,0 +1 @@
|
|||||||
|
001012082101039,1234,internet|ims_sig,internet|ims_sig,321321,255,321312,32131,32131
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
001011100001157,1234567890ABCDEF1234567890ABCDEF,0,8000,11111111111111111111111111111111
|
||||||
|
001011100001158,1234567890ABCDEF1234567890ABCDEF,0,8000,11111111111111111111111111111111
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
001011100001157,62357000583,def_ambr,def_nssai,def_arfb,def_sar,0,3,def_snssai,1-000001&internet&ims,1,64,24,65,def_eps,1,010200000000,-
|
||||||
|
001011100001158,62357000585,def_ambr,def_nssai,def_arfb,def_sar,0,3,def_snssai,1-000001&internet&ims,1,64,24,65,def_eps,1,010200000000,-
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
62357000580,123456
|
||||||
|
62357000581,123456
|
||||||
@@ -0,0 +1,2 @@
|
|||||||
|
001012082101039,62357000580,1,ims.mnc001.mcc001.3gppnetwork.org
|
||||||
|
62357000581,62357000581,0,ims.mnc001.mcc001.3gppnetwork.org
|
||||||
@@ -0,0 +1,28 @@
|
|||||||
|
<svg width="1024" height="1024" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<!-- Created with Method Draw - http://github.com/duopixel/Method-Draw/ -->
|
||||||
|
|
||||||
|
<g>
|
||||||
|
<title>background</title>
|
||||||
|
<rect fill="none" id="canvas_background" height="1026" width="1026" y="-1" x="-1"/>
|
||||||
|
<g display="none" overflow="visible" y="0" x="0" height="100%" width="100%" id="canvasGrid">
|
||||||
|
<rect fill="url(#gridpattern)" stroke-width="0" y="1" x="1" height="768" width="1024"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
<g>
|
||||||
|
<title>Layer 1</title>
|
||||||
|
<g stroke="null" id="svg_15">
|
||||||
|
<path stroke="null" id="svg_4" fill="#B5D6FB" d="m512.094844,961.632039c-1.327621,0 -2.560412,-0.405439 -3.793202,-1.114958l-405.588164,-251.575028c-2.275921,-1.419037 -3.698372,-4.054392 -3.698372,-6.892467l0,-90.007504c0,-2.838074 1.422451,-5.473429 3.698372,-6.892467l405.588164,-255.426701c1.137961,-0.709519 2.465582,-1.114958 3.793202,-1.114958s2.655242,0.405439 3.793202,1.114958l405.493334,255.426701c2.275921,1.419037 3.698372,4.054392 3.698372,6.892467l0,90.007504c0,2.838074 -1.422451,5.473429 -3.698372,6.892467l-405.588164,251.575028c-1.137961,0.709519 -2.465582,1.114958 -3.698372,1.114958z"/>
|
||||||
|
<path stroke="null" id="svg_5" fill="#0276F7" d="m512.094844,356.615382l405.398504,255.426701l0,90.007504l-66.096551,40.94936l-339.301952,210.625668l-339.491613,-210.625668l-66.096551,-40.94936l0,-90.007504l405.588164,-255.426701m0,-16.014849c-2.655242,0 -5.215653,0.709519 -7.586405,2.229916l-405.588164,255.426701c-4.551843,2.838074 -7.396745,8.108784 -7.396745,13.784933l0,90.007504c0,5.676149 2.844902,10.946859 7.491575,13.886293l66.096551,41.05072l339.491613,210.625668c2.275921,1.419037 4.931163,2.128556 7.491575,2.128556s5.215653,-0.709519 7.491575,-2.128556l339.301952,-210.625668l66.096551,-40.94936c4.646673,-2.838074 7.491575,-8.108784 7.491575,-13.886293l0,-90.007504c0,-5.676149 -2.844902,-10.946859 -7.396745,-13.784933l-405.398504,-255.426701c-2.370751,-1.520397 -5.025993,-2.331275 -7.586405,-2.331275z"/>
|
||||||
|
<path stroke="null" id="svg_6" fill="#FFFFFF" d="m106.50668,612.042083l405.493334,253.298145l405.493334,-253.298145l-405.398504,-255.426701l-405.588164,255.426701z"/>
|
||||||
|
<path stroke="null" id="svg_7" fill="#D4E4FC" d="m501.473877,64.192353l-254.9032,498.487506l263.343075,161.162085l266.662127,-162.074323l-275.102002,-497.575268z"/>
|
||||||
|
<path stroke="null" id="svg_8" fill="#0276F7" d="m229.975417,602.311542c-1.232791,0 -2.465582,-0.304079 -3.698372,-1.013598c-3.603542,-2.128556 -4.931163,-6.993826 -2.844902,-10.845499l279.653845,-532.13896c1.327621,-2.533995 3.793202,-4.054392 6.543274,-4.054392c2.655242,0 5.120823,1.520397 6.543274,4.054392l284.395348,532.13896c2.086261,3.851672 0.75864,8.716943 -2.750072,10.946859c-3.603542,2.128556 -8.155385,0.810878 -10.241646,-2.939434l-277.852074,-519.874424l-273.205401,519.671704c-1.422451,2.635355 -3.982862,4.054392 -6.543274,4.054392z"/>
|
||||||
|
<path stroke="null" id="svg_9" fill="#0276F7" d="m509.913752,755.567562c-4.172523,0 -7.491575,-3.547593 -7.491575,-8.007424l0,-666.744777c0,-4.459831 3.319052,-8.007424 7.491575,-8.007424s7.491575,3.547593 7.491575,8.007424l0,666.846137c0,4.358471 -3.413882,7.906065 -7.491575,7.906065z"/>
|
||||||
|
<path stroke="null" id="svg_10" fill="#0276F7" d="m509.913752,731.849369c-1.327621,0 -2.560412,-0.405439 -3.698372,-1.013598l-263.343075,-161.162085c-3.603542,-2.229916 -4.836333,-7.095186 -2.750072,-10.946859c2.086261,-3.851672 6.638104,-5.16935 10.241646,-2.939434l259.549873,158.83081l262.963755,-159.844408c3.603542,-2.229916 8.155385,-0.810878 10.241646,3.040794c2.086261,3.851672 0.75864,8.716943 -2.844902,10.946859l-266.662127,162.074323c-1.137961,0.709519 -2.465582,1.013598 -3.698372,1.013598z"/>
|
||||||
|
<path stroke="null" id="svg_11" fill="#0276F7" d="m509.913752,579.708306c-1.327621,0 -2.560412,-0.405439 -3.793202,-1.114958l-201.988026,-125.686154c-3.603542,-2.229916 -4.741503,-7.095186 -2.750072,-10.946859c2.086261,-3.851672 6.638104,-5.16935 10.241646,-2.838074l198.289654,123.354879l201.798366,-122.138561c3.603542,-2.229916 8.155385,-0.810878 10.241646,3.040794c2.086261,3.851672 0.75864,8.716943 -2.844902,10.845499l-205.496739,124.469837c-1.137961,0.709519 -2.465582,1.013598 -3.698372,1.013598zm-2.465582,-157.513132c-1.232791,0 -2.370751,-0.304079 -3.508712,-0.912238l-140.917468,-79.668804c-3.698372,-2.128556 -5.025993,-6.892467 -3.129392,-10.845499c1.896601,-3.953032 6.448444,-5.37207 10.146816,-3.344873l137.503586,77.742968l143.00373,-79.871524c3.698372,-2.027196 8.155385,-0.506799 10.146816,3.344873c1.896601,3.953032 0.47415,8.716943 -3.129392,10.845499l-146.512442,81.79736c-1.232791,0.608159 -2.370751,0.912238 -3.603542,0.912238zm2.465582,-148.49211c-1.232791,0 -2.465582,-0.304079 -3.508712,-0.912238l-82.312492,-47.436387c-3.603542,-2.128556 -5.025993,-6.993826 -3.034562,-10.845499c1.991431,-3.953032 6.543274,-5.27071 10.146816,-3.243514l78.708949,45.409191l78.329629,-47.537747c3.603542,-2.229916 8.155385,-0.810878 10.241646,3.040794c2.086261,3.851672 0.75864,8.716943 -2.844902,10.946859l-81.933171,49.666303c-1.232791,0.608159 -2.560412,0.912238 -3.793202,0.912238z"/>
|
||||||
|
<path stroke="null" id="svg_12" fill="#0276F7" d="m509.913752,579.708306l-0.28449,0l-263.248245,-9.021022c-4.172523,-0.10136 -7.396745,-3.851672 -7.207085,-8.210144c0.09483,-4.459831 4.077693,-7.703345 7.681235,-7.703345l263.343075,9.021022c4.172523,0.10136 7.396745,3.851672 7.207085,8.210144c-0.18966,4.257112 -3.508712,7.703345 -7.491575,7.703345zm0,152.141063c-1.612111,0 -3.224222,-0.608159 -4.646673,-1.723117c-3.224222,-2.736715 -3.793202,-7.804705 -1.232791,-11.250938l205.496739,-276.610899c2.560412,-3.446233 7.301915,-4.054392 10.526137,-1.317677c3.224222,2.736715 3.793202,7.804705 1.232791,11.250938l-205.496739,276.610899c-1.517281,2.027196 -3.698372,3.040794 -5.879464,3.040794z"/>
|
||||||
|
<path stroke="null" id="svg_13" fill="#0276F7" d="m509.913752,579.708306c-1.422451,0 -2.750072,-0.405439 -4.077693,-1.216318c-3.508712,-2.432635 -4.457013,-7.297906 -2.275921,-11.048218l144.14169,-239.310492c2.275921,-3.750313 6.922594,-4.763911 10.336476,-2.432635c3.508712,2.432635 4.457013,7.297906 2.275921,11.048218l-144.14169,239.310492c-1.422451,2.331275 -3.793202,3.648953 -6.258784,3.648953zm-2.465582,-157.513132c-1.043131,0 -2.086261,-0.20272 -3.129392,-0.709519c-3.793202,-1.824476 -5.405313,-6.588387 -3.698372,-10.642779l84.398753,-198.158413c1.706941,-4.054392 6.069124,-5.777509 9.957156,-3.953032c3.793202,1.824476 5.405313,6.588387 3.698372,10.642779l-84.303923,198.158413c-1.327621,2.939434 -4.077693,4.662551 -6.922594,4.662551z"/>
|
||||||
|
<path stroke="null" id="svg_14" fill="#0276F7" d="m591.846924,375.062866c-2.750072,0 -5.405313,-1.621757 -6.732934,-4.459831c-1.801771,-3.953032 -0.28449,-8.716943 3.413882,-10.642779l129.253371,-67.302908l-365.759539,-178.089172l20.862613,208.091673l133.994874,-64.262114c3.698372,-1.824476 8.155385,0 9.862326,4.054392c1.706941,4.054392 0,8.716943 -3.793202,10.541419l-143.38305,68.823305c-2.181091,1.013598 -4.646673,0.912238 -6.827764,-0.405439c-2.086261,-1.317677 -3.413882,-3.547593 -3.698372,-6.081588l-23.328195,-233.026185c-0.28449,-2.838074 0.853471,-5.676149 3.034562,-7.297906c2.181091,-1.621757 5.025993,-2.027196 7.491575,-0.810878l392.217126,190.961867c2.655242,1.317677 4.362183,4.054392 4.362183,7.196546c0,3.142154 -1.612111,5.980228 -4.172523,7.297906l-143.57271,74.600814c-1.043131,0.608159 -2.181091,0.810878 -3.224222,0.810878zm-283.921198,78.959286c-3.603542,0 -6.827764,-2.838074 -7.396745,-6.791107c-0.56898,-4.358471 2.181091,-8.412864 6.258784,-9.122382l199.617275,-31.826978c4.077693,-0.608159 7.870895,2.331275 8.534705,6.689747c0.56898,4.358471 -2.181091,8.412864 -6.258784,9.122382l-199.617275,31.826978c-0.47415,0.10136 -0.853471,0.10136 -1.137961,0.10136z"/>
|
||||||
|
</g>
|
||||||
|
<text stroke="null" font-style="italic" transform="matrix(6.577099502228161,0,0,7.449448263868419,-1073.2057632249744,-908.8606073938396) " xml:space="preserve" text-anchor="start" font-family="Arvo, sans-serif" font-size="24" id="svg_16" y="177.898525" x="178.621382" stroke-width="0" fill="#B5D6FB">4G</text>
|
||||||
|
</g>
|
||||||
|
</svg>
|
||||||
|
After Width: | Height: | Size: 7.9 KiB |
@@ -0,0 +1,28 @@
|
|||||||
|
<svg width="1024" height="1024" xmlns="http://www.w3.org/2000/svg">
|
||||||
|
<!-- Created with Method Draw - http://github.com/duopixel/Method-Draw/ -->
|
||||||
|
|
||||||
|
<g>
|
||||||
|
<title>background</title>
|
||||||
|
<rect fill="none" id="canvas_background" height="1026" width="1026" y="-1" x="-1"/>
|
||||||
|
<g display="none" overflow="visible" y="0" x="0" height="100%" width="100%" id="canvasGrid">
|
||||||
|
<rect fill="url(#gridpattern)" stroke-width="0" y="1" x="1" height="768" width="1024"/>
|
||||||
|
</g>
|
||||||
|
</g>
|
||||||
|
<g>
|
||||||
|
<title>Layer 1</title>
|
||||||
|
<g stroke="null" id="svg_15">
|
||||||
|
<path stroke="null" id="svg_4" fill="#B5D6FB" d="m512.094844,961.632039c-1.327621,0 -2.560412,-0.405439 -3.793202,-1.114958l-405.588164,-251.575028c-2.275921,-1.419037 -3.698372,-4.054392 -3.698372,-6.892467l0,-90.007504c0,-2.838074 1.422451,-5.473429 3.698372,-6.892467l405.588164,-255.426701c1.137961,-0.709519 2.465582,-1.114958 3.793202,-1.114958s2.655242,0.405439 3.793202,1.114958l405.493334,255.426701c2.275921,1.419037 3.698372,4.054392 3.698372,6.892467l0,90.007504c0,2.838074 -1.422451,5.473429 -3.698372,6.892467l-405.588164,251.575028c-1.137961,0.709519 -2.465582,1.114958 -3.698372,1.114958z"/>
|
||||||
|
<path stroke="null" id="svg_5" fill="#0276F7" d="m512.094844,356.615382l405.398504,255.426701l0,90.007504l-66.096551,40.94936l-339.301952,210.625668l-339.491613,-210.625668l-66.096551,-40.94936l0,-90.007504l405.588164,-255.426701m0,-16.014849c-2.655242,0 -5.215653,0.709519 -7.586405,2.229916l-405.588164,255.426701c-4.551843,2.838074 -7.396745,8.108784 -7.396745,13.784933l0,90.007504c0,5.676149 2.844902,10.946859 7.491575,13.886293l66.096551,41.05072l339.491613,210.625668c2.275921,1.419037 4.931163,2.128556 7.491575,2.128556s5.215653,-0.709519 7.491575,-2.128556l339.301952,-210.625668l66.096551,-40.94936c4.646673,-2.838074 7.491575,-8.108784 7.491575,-13.886293l0,-90.007504c0,-5.676149 -2.844902,-10.946859 -7.396745,-13.784933l-405.398504,-255.426701c-2.370751,-1.520397 -5.025993,-2.331275 -7.586405,-2.331275z"/>
|
||||||
|
<path stroke="null" id="svg_6" fill="#FFFFFF" d="m106.50668,612.042083l405.493334,253.298145l405.493334,-253.298145l-405.398504,-255.426701l-405.588164,255.426701z"/>
|
||||||
|
<path stroke="null" id="svg_7" fill="#D4E4FC" d="m501.473877,64.192353l-254.9032,498.487506l263.343075,161.162085l266.662127,-162.074323l-275.102002,-497.575268z"/>
|
||||||
|
<path stroke="null" id="svg_8" fill="#0276F7" d="m229.975417,602.311542c-1.232791,0 -2.465582,-0.304079 -3.698372,-1.013598c-3.603542,-2.128556 -4.931163,-6.993826 -2.844902,-10.845499l279.653845,-532.13896c1.327621,-2.533995 3.793202,-4.054392 6.543274,-4.054392c2.655242,0 5.120823,1.520397 6.543274,4.054392l284.395348,532.13896c2.086261,3.851672 0.75864,8.716943 -2.750072,10.946859c-3.603542,2.128556 -8.155385,0.810878 -10.241646,-2.939434l-277.852074,-519.874424l-273.205401,519.671704c-1.422451,2.635355 -3.982862,4.054392 -6.543274,4.054392z"/>
|
||||||
|
<path stroke="null" id="svg_9" fill="#0276F7" d="m509.913752,755.567562c-4.172523,0 -7.491575,-3.547593 -7.491575,-8.007424l0,-666.744777c0,-4.459831 3.319052,-8.007424 7.491575,-8.007424s7.491575,3.547593 7.491575,8.007424l0,666.846137c0,4.358471 -3.413882,7.906065 -7.491575,7.906065z"/>
|
||||||
|
<path stroke="null" id="svg_10" fill="#0276F7" d="m509.913752,731.849369c-1.327621,0 -2.560412,-0.405439 -3.698372,-1.013598l-263.343075,-161.162085c-3.603542,-2.229916 -4.836333,-7.095186 -2.750072,-10.946859c2.086261,-3.851672 6.638104,-5.16935 10.241646,-2.939434l259.549873,158.83081l262.963755,-159.844408c3.603542,-2.229916 8.155385,-0.810878 10.241646,3.040794c2.086261,3.851672 0.75864,8.716943 -2.844902,10.946859l-266.662127,162.074323c-1.137961,0.709519 -2.465582,1.013598 -3.698372,1.013598z"/>
|
||||||
|
<path stroke="null" id="svg_11" fill="#0276F7" d="m509.913752,579.708306c-1.327621,0 -2.560412,-0.405439 -3.793202,-1.114958l-201.988026,-125.686154c-3.603542,-2.229916 -4.741503,-7.095186 -2.750072,-10.946859c2.086261,-3.851672 6.638104,-5.16935 10.241646,-2.838074l198.289654,123.354879l201.798366,-122.138561c3.603542,-2.229916 8.155385,-0.810878 10.241646,3.040794c2.086261,3.851672 0.75864,8.716943 -2.844902,10.845499l-205.496739,124.469837c-1.137961,0.709519 -2.465582,1.013598 -3.698372,1.013598zm-2.465582,-157.513132c-1.232791,0 -2.370751,-0.304079 -3.508712,-0.912238l-140.917468,-79.668804c-3.698372,-2.128556 -5.025993,-6.892467 -3.129392,-10.845499c1.896601,-3.953032 6.448444,-5.37207 10.146816,-3.344873l137.503586,77.742968l143.00373,-79.871524c3.698372,-2.027196 8.155385,-0.506799 10.146816,3.344873c1.896601,3.953032 0.47415,8.716943 -3.129392,10.845499l-146.512442,81.79736c-1.232791,0.608159 -2.370751,0.912238 -3.603542,0.912238zm2.465582,-148.49211c-1.232791,0 -2.465582,-0.304079 -3.508712,-0.912238l-82.312492,-47.436387c-3.603542,-2.128556 -5.025993,-6.993826 -3.034562,-10.845499c1.991431,-3.953032 6.543274,-5.27071 10.146816,-3.243514l78.708949,45.409191l78.329629,-47.537747c3.603542,-2.229916 8.155385,-0.810878 10.241646,3.040794c2.086261,3.851672 0.75864,8.716943 -2.844902,10.946859l-81.933171,49.666303c-1.232791,0.608159 -2.560412,0.912238 -3.793202,0.912238z"/>
|
||||||
|
<path stroke="null" id="svg_12" fill="#0276F7" d="m509.913752,579.708306l-0.28449,0l-263.248245,-9.021022c-4.172523,-0.10136 -7.396745,-3.851672 -7.207085,-8.210144c0.09483,-4.459831 4.077693,-7.703345 7.681235,-7.703345l263.343075,9.021022c4.172523,0.10136 7.396745,3.851672 7.207085,8.210144c-0.18966,4.257112 -3.508712,7.703345 -7.491575,7.703345zm0,152.141063c-1.612111,0 -3.224222,-0.608159 -4.646673,-1.723117c-3.224222,-2.736715 -3.793202,-7.804705 -1.232791,-11.250938l205.496739,-276.610899c2.560412,-3.446233 7.301915,-4.054392 10.526137,-1.317677c3.224222,2.736715 3.793202,7.804705 1.232791,11.250938l-205.496739,276.610899c-1.517281,2.027196 -3.698372,3.040794 -5.879464,3.040794z"/>
|
||||||
|
<path stroke="null" id="svg_13" fill="#0276F7" d="m509.913752,579.708306c-1.422451,0 -2.750072,-0.405439 -4.077693,-1.216318c-3.508712,-2.432635 -4.457013,-7.297906 -2.275921,-11.048218l144.14169,-239.310492c2.275921,-3.750313 6.922594,-4.763911 10.336476,-2.432635c3.508712,2.432635 4.457013,7.297906 2.275921,11.048218l-144.14169,239.310492c-1.422451,2.331275 -3.793202,3.648953 -6.258784,3.648953zm-2.465582,-157.513132c-1.043131,0 -2.086261,-0.20272 -3.129392,-0.709519c-3.793202,-1.824476 -5.405313,-6.588387 -3.698372,-10.642779l84.398753,-198.158413c1.706941,-4.054392 6.069124,-5.777509 9.957156,-3.953032c3.793202,1.824476 5.405313,6.588387 3.698372,10.642779l-84.303923,198.158413c-1.327621,2.939434 -4.077693,4.662551 -6.922594,4.662551z"/>
|
||||||
|
<path stroke="null" id="svg_14" fill="#0276F7" d="m591.846924,375.062866c-2.750072,0 -5.405313,-1.621757 -6.732934,-4.459831c-1.801771,-3.953032 -0.28449,-8.716943 3.413882,-10.642779l129.253371,-67.302908l-365.759539,-178.089172l20.862613,208.091673l133.994874,-64.262114c3.698372,-1.824476 8.155385,0 9.862326,4.054392c1.706941,4.054392 0,8.716943 -3.793202,10.541419l-143.38305,68.823305c-2.181091,1.013598 -4.646673,0.912238 -6.827764,-0.405439c-2.086261,-1.317677 -3.413882,-3.547593 -3.698372,-6.081588l-23.328195,-233.026185c-0.28449,-2.838074 0.853471,-5.676149 3.034562,-7.297906c2.181091,-1.621757 5.025993,-2.027196 7.491575,-0.810878l392.217126,190.961867c2.655242,1.317677 4.362183,4.054392 4.362183,7.196546c0,3.142154 -1.612111,5.980228 -4.172523,7.297906l-143.57271,74.600814c-1.043131,0.608159 -2.181091,0.810878 -3.224222,0.810878zm-283.921198,78.959286c-3.603542,0 -6.827764,-2.838074 -7.396745,-6.791107c-0.56898,-4.358471 2.181091,-8.412864 6.258784,-9.122382l199.617275,-31.826978c4.077693,-0.608159 7.870895,2.331275 8.534705,6.689747c0.56898,4.358471 -2.181091,8.412864 -6.258784,9.122382l-199.617275,31.826978c-0.47415,0.10136 -0.853471,0.10136 -1.137961,0.10136z"/>
|
||||||
|
</g>
|
||||||
|
<text stroke="null" font-style="italic" transform="matrix(6.577099502228161,0,0,7.449448263868419,-1073.2057632249744,-908.8606073938396) " xml:space="preserve" text-anchor="start" font-family="Arvo, sans-serif" font-size="24" id="svg_16" y="177.898525" x="178.621382" stroke-width="0" fill="#D4E4FC">5G</text>
|
||||||
|
</g>
|
||||||
|
</svg>
|
||||||
|
After Width: | Height: | Size: 7.9 KiB |
@@ -9,6 +9,8 @@ import advancedFormat from 'dayjs/plugin/advancedFormat';
|
|||||||
import useLayoutStore from '@/store/modules/layout';
|
import useLayoutStore from '@/store/modules/layout';
|
||||||
import useAppStore from '@/store/modules/app';
|
import useAppStore from '@/store/modules/app';
|
||||||
import useI18n from '@/hooks/useI18n';
|
import useI18n from '@/hooks/useI18n';
|
||||||
|
import { CACHE_LOCAL_PROCONFIG } from './constants/cache-keys-constants';
|
||||||
|
import { localRemove } from './utils/cache-local-utils';
|
||||||
const { t, currentLocale } = useI18n();
|
const { t, currentLocale } = useI18n();
|
||||||
const { themeConfig, initPrimaryColor, changeConf } = useLayoutStore();
|
const { themeConfig, initPrimaryColor, changeConf } = useLayoutStore();
|
||||||
dayjs.extend(advancedFormat);
|
dayjs.extend(advancedFormat);
|
||||||
@@ -34,6 +36,7 @@ onBeforeMount(() => {
|
|||||||
maxCount: 15,
|
maxCount: 15,
|
||||||
});
|
});
|
||||||
initPrimaryColor();
|
initPrimaryColor();
|
||||||
|
localRemove(CACHE_LOCAL_PROCONFIG);
|
||||||
|
|
||||||
// 输出应用版本号
|
// 输出应用版本号
|
||||||
const appStore = useAppStore();
|
const appStore = useAppStore();
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
import { parseObjLineToHump } from '@/utils/parse-utils';
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
import { parseDateToStr, YYYY_MM_DD_HH_MM_SS } from '@/utils/date-utils';
|
||||||
import useUserStore from '@/store/modules/user';
|
import useUserStore from '@/store/modules/user';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -122,7 +122,7 @@ export function updateConfirm(data: Record<string, any>) {
|
|||||||
const userName = useUserStore().userName;
|
const userName = useUserStore().userName;
|
||||||
let finalData = {
|
let finalData = {
|
||||||
alarm: {
|
alarm: {
|
||||||
ack_time: parseDateToStr(time),
|
ack_time: parseDateToStr(time, YYYY_MM_DD_HH_MM_SS),
|
||||||
ack_user: userName,
|
ack_user: userName,
|
||||||
ack_state: '1',
|
ack_state: '1',
|
||||||
},
|
},
|
||||||
@@ -145,7 +145,7 @@ export function cancelConfirm(data: (string | number)[]) {
|
|||||||
const userName = useUserStore().userName;
|
const userName = useUserStore().userName;
|
||||||
let finalData = {
|
let finalData = {
|
||||||
alarm: {
|
alarm: {
|
||||||
ack_time: parseDateToStr(time),
|
ack_time: parseDateToStr(time, YYYY_MM_DD_HH_MM_SS),
|
||||||
ack_user: '',
|
ack_user: '',
|
||||||
ack_state: '0',
|
ack_state: '0',
|
||||||
},
|
},
|
||||||
@@ -211,12 +211,12 @@ export function getPass() {
|
|||||||
* @param data 鉴权对象
|
* @param data 鉴权对象
|
||||||
* @returns object
|
* @returns object
|
||||||
*/
|
*/
|
||||||
export function clearAlarm(data: Record<string, any>) {
|
export function clearAlarm2(data: Record<string, any>) {
|
||||||
var time = new Date();
|
var time = new Date();
|
||||||
const userName = useUserStore().userName;
|
const userName = useUserStore().userName;
|
||||||
let finalData = {
|
let finalData = {
|
||||||
data: {
|
data: {
|
||||||
clear_time: parseDateToStr(time),
|
clear_time: parseDateToStr(time, YYYY_MM_DD_HH_MM_SS),
|
||||||
clear_type: '2',
|
clear_type: '2',
|
||||||
alarm_status: '0',
|
alarm_status: '0',
|
||||||
clear_user: userName,
|
clear_user: userName,
|
||||||
@@ -232,6 +232,19 @@ export function clearAlarm(data: Record<string, any>) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 清除告警信息
|
||||||
|
* @param ids 记录ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function clearAlarm(ids: string[]) {
|
||||||
|
return request({
|
||||||
|
url: `/neData/alarm/clear`,
|
||||||
|
method: 'PUT',
|
||||||
|
data: { ids },
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 手工同步
|
* 手工同步
|
||||||
* @param data 鉴权对象
|
* @param data 鉴权对象
|
||||||
@@ -360,3 +373,137 @@ export async function top3Sel(filterFlag?: string) {
|
|||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
export async function alarmDashGetAct() {
|
||||||
|
let totalSQL = `select count(*) as total from alarm where alarm_status='1' `;
|
||||||
|
let rowsSQL = `select ne_type,alarm_id,alarm_title,orig_severity,event_time from alarm WHERE alarm_status='1' and orig_severity!='Event' order by event_time desc limit 0,10 `;
|
||||||
|
// 查询
|
||||||
|
|
||||||
|
|
||||||
|
// 发起请求
|
||||||
|
const result = await request({
|
||||||
|
url: `/api/rest/databaseManagement/v1/select/omc_db/alarm`,
|
||||||
|
method: 'get',
|
||||||
|
params: {
|
||||||
|
SQL: totalSQL,
|
||||||
|
rowsSQL: rowsSQL,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
// 解析数据
|
||||||
|
if (result.code === RESULT_CODE_SUCCESS) {
|
||||||
|
const data: DataList = {
|
||||||
|
total: 0,
|
||||||
|
rows: [],
|
||||||
|
code: result.code,
|
||||||
|
msg: result.msg,
|
||||||
|
};
|
||||||
|
result.data.data.forEach((item: any) => {
|
||||||
|
const itemData = item['alarm'];
|
||||||
|
if (Array.isArray(itemData)) {
|
||||||
|
if (itemData.length === 1 && itemData[0]['total'] >= 0) {
|
||||||
|
data.total = itemData[0]['total'];
|
||||||
|
} else {
|
||||||
|
data.rows = itemData.map(v => parseObjLineToHump(v));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return data;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
export async function alarmDashGetHis() {
|
||||||
|
let totalSQL = `select count(*) as total from alarm where alarm_status='0' `;
|
||||||
|
let rowsSQL = `select ne_type,alarm_id,alarm_title,orig_severity,event_time from alarm WHERE alarm_status='0' and orig_severity!='Event' order by event_time desc limit 0,10 `;
|
||||||
|
// 查询
|
||||||
|
|
||||||
|
|
||||||
|
// 发起请求
|
||||||
|
const result = await request({
|
||||||
|
url: `/api/rest/databaseManagement/v1/select/omc_db/alarm`,
|
||||||
|
method: 'get',
|
||||||
|
params: {
|
||||||
|
SQL: totalSQL,
|
||||||
|
rowsSQL: rowsSQL,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
// 解析数据
|
||||||
|
if (result.code === RESULT_CODE_SUCCESS) {
|
||||||
|
const data: DataList = {
|
||||||
|
total: 0,
|
||||||
|
rows: [],
|
||||||
|
code: result.code,
|
||||||
|
msg: result.msg,
|
||||||
|
};
|
||||||
|
result.data.data.forEach((item: any) => {
|
||||||
|
const itemData = item['alarm'];
|
||||||
|
if (Array.isArray(itemData)) {
|
||||||
|
if (itemData.length === 1 && itemData[0]['total'] >= 0) {
|
||||||
|
data.total = itemData[0]['total'];
|
||||||
|
} else {
|
||||||
|
data.rows = itemData.map(v => parseObjLineToHump(v));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return data;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
export async function getAlarmTrend(params: any) {
|
||||||
|
const days = Number(params.days || 1);
|
||||||
|
let groupFormat = days === 1 ? '%H:00' : '%Y-%m-%d';
|
||||||
|
let timeCondition = days === 1
|
||||||
|
? `event_time >= DATE_SUB(NOW(), INTERVAL 1 DAY)`
|
||||||
|
: `event_time >= DATE_SUB(CURDATE(), INTERVAL ${days} DAY)`;
|
||||||
|
let totalSQL = `select count(*) as total from alarm where alarm_status='0' `;
|
||||||
|
|
||||||
|
let rowsSQL = ` SELECT
|
||||||
|
DATE_FORMAT(event_time, '${groupFormat}') AS time,
|
||||||
|
SUM(CASE WHEN orig_severity='Critical' THEN 1 ELSE 0 END) AS Critical,
|
||||||
|
SUM(CASE WHEN orig_severity='Major' THEN 1 ELSE 0 END) AS Major,
|
||||||
|
SUM(CASE WHEN orig_severity='Minor' THEN 1 ELSE 0 END) AS Minor,
|
||||||
|
SUM(CASE WHEN orig_severity='Warning' THEN 1 ELSE 0 END) AS Warning
|
||||||
|
FROM alarm
|
||||||
|
WHERE alarm_status='0'
|
||||||
|
AND ${timeCondition}
|
||||||
|
GROUP BY time
|
||||||
|
ORDER BY time ASC `;
|
||||||
|
// 查询
|
||||||
|
|
||||||
|
|
||||||
|
// 发起请求
|
||||||
|
const result = await request({
|
||||||
|
url: `/api/rest/databaseManagement/v1/select/omc_db/alarm`,
|
||||||
|
method: 'get',
|
||||||
|
params: {
|
||||||
|
SQL: totalSQL,
|
||||||
|
rowsSQL: rowsSQL,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
// 解析数据
|
||||||
|
if (result.code === RESULT_CODE_SUCCESS) {
|
||||||
|
const data: DataList = {
|
||||||
|
total: 0,
|
||||||
|
rows: [],
|
||||||
|
code: result.code,
|
||||||
|
msg: result.msg,
|
||||||
|
};
|
||||||
|
result.data.data.forEach((item: any) => {
|
||||||
|
const itemData = item['alarm'];
|
||||||
|
if (Array.isArray(itemData)) {
|
||||||
|
if (itemData.length === 1 && itemData[0]['total'] >= 0) {
|
||||||
|
data.total = itemData[0]['total'];
|
||||||
|
} else {
|
||||||
|
data.rows = itemData.map(v => parseObjLineToHump(v));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return data;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
@@ -1,8 +1,6 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
import { parseObjLineToHump } from '@/utils/parse-utils';
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
|
||||||
import useUserStore from '@/store/modules/user';
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 查询列表
|
* 查询列表
|
||||||
|
|||||||
@@ -63,7 +63,11 @@ export async function getAlarmSet() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (Object.keys(resultData).length === 0) {
|
if (Object.keys(resultData).length === 0) {
|
||||||
return { code: RESULT_CODE_ERROR, msg: RESULT_MSG_ERROR[language], data: {} };
|
return {
|
||||||
|
code: RESULT_CODE_ERROR,
|
||||||
|
msg: RESULT_MSG_ERROR[language],
|
||||||
|
data: {},
|
||||||
|
};
|
||||||
}
|
}
|
||||||
return {
|
return {
|
||||||
code: RESULT_CODE_SUCCESS,
|
code: RESULT_CODE_SUCCESS,
|
||||||
@@ -117,7 +121,11 @@ export async function updateAlarmSet(data: Record<string, any>) {
|
|||||||
}
|
}
|
||||||
// 无变更时
|
// 无变更时
|
||||||
if (resultNum === 0) {
|
if (resultNum === 0) {
|
||||||
return { code: RESULT_CODE_ERROR, msg: RESULT_MSG_ERROR[language], data: 0 };
|
return {
|
||||||
|
code: RESULT_CODE_ERROR,
|
||||||
|
msg: RESULT_MSG_ERROR[language],
|
||||||
|
data: 0,
|
||||||
|
};
|
||||||
}
|
}
|
||||||
return {
|
return {
|
||||||
code: RESULT_CODE_SUCCESS,
|
code: RESULT_CODE_SUCCESS,
|
||||||
@@ -166,11 +174,10 @@ export async function getForwardSet() {
|
|||||||
*/
|
*/
|
||||||
export async function updateForwardSet(data: Record<string, any>) {
|
export async function updateForwardSet(data: Record<string, any>) {
|
||||||
// return false;
|
// return false;
|
||||||
console.log(data)
|
let obj: any = [
|
||||||
let obj:any=[
|
{ interface: 'Email', to_user: data.emailObj },
|
||||||
{interface:"Email",to_user:data.emailObj},
|
{ interface: 'SMS', to_user: data.smsObj },
|
||||||
{interface:"SMS",to_user:data.smsObj}
|
];
|
||||||
]
|
|
||||||
const result = await request({
|
const result = await request({
|
||||||
url: `/api/rest/databaseManagement/v1/omc_db/config?WHERE=config_tag='forwardAlarm'`,
|
url: `/api/rest/databaseManagement/v1/omc_db/config?WHERE=config_tag='forwardAlarm'`,
|
||||||
method: 'put',
|
method: 'put',
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
import { parseObjLineToHump } from '@/utils/parse-utils';
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
import { parseDateToStr, YYYY_MM_DD_HH_MM_SS } from '@/utils/date-utils';
|
||||||
import useUserStore from '@/store/modules/user';
|
import useUserStore from '@/store/modules/user';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -79,7 +79,7 @@ export function updateConfirm(data: Record<string, any>) {
|
|||||||
const userName = useUserStore().userName;
|
const userName = useUserStore().userName;
|
||||||
let finalData = {
|
let finalData = {
|
||||||
alarm: {
|
alarm: {
|
||||||
ack_time: parseDateToStr(time),
|
ack_time: parseDateToStr(time, YYYY_MM_DD_HH_MM_SS),
|
||||||
ack_user: userName,
|
ack_user: userName,
|
||||||
ack_state: '1',
|
ack_state: '1',
|
||||||
},
|
},
|
||||||
@@ -101,7 +101,7 @@ export function cancelConfirm(data: (string | number)[]) {
|
|||||||
var time = new Date();
|
var time = new Date();
|
||||||
let finalData = {
|
let finalData = {
|
||||||
alarm: {
|
alarm: {
|
||||||
ack_time: parseDateToStr(time),
|
ack_time: parseDateToStr(time, YYYY_MM_DD_HH_MM_SS),
|
||||||
ack_user: '',
|
ack_user: '',
|
||||||
ack_state: '0',
|
ack_state: '0',
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -1,3 +1,5 @@
|
|||||||
|
import { CACHE_SESSION_CRYPTO_API } from '@/constants/cache-keys-constants';
|
||||||
|
import { sessionGet } from '@/utils/cache-session-utils';
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -51,3 +53,43 @@ export function delFile(query: Record<string, any>) {
|
|||||||
params: query,
|
params: query,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 更新FTP信息
|
||||||
|
* @param data 数据
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function updateFTPInfo(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/lm/table/ftp`,
|
||||||
|
method: 'post',
|
||||||
|
data: data,
|
||||||
|
crypto: sessionGet(CACHE_SESSION_CRYPTO_API) !== 'false',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 获取FTP信息
|
||||||
|
* @param data 数据
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getFTPInfo() {
|
||||||
|
return request({
|
||||||
|
url: `/lm/table/ftp`,
|
||||||
|
method: 'get',
|
||||||
|
crypto: sessionGet(CACHE_SESSION_CRYPTO_API) !== 'false',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 发送FTP文件
|
||||||
|
* @param data 数据
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function putFTPInfo(filePath: string, fileName: string) {
|
||||||
|
return request({
|
||||||
|
url: `/lm/table/ftp`,
|
||||||
|
method: 'put',
|
||||||
|
data: { filePath, fileName },
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -1,3 +1,5 @@
|
|||||||
|
import { CACHE_SESSION_CRYPTO_API } from '@/constants/cache-keys-constants';
|
||||||
|
import { sessionGet } from '@/utils/cache-session-utils';
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
// 登录方法
|
// 登录方法
|
||||||
@@ -7,7 +9,7 @@ export function login(data: Record<string, string>) {
|
|||||||
method: 'post',
|
method: 'post',
|
||||||
data: data,
|
data: data,
|
||||||
whithToken: false,
|
whithToken: false,
|
||||||
crypto: true,
|
crypto: sessionGet(CACHE_SESSION_CRYPTO_API) !== 'false',
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -22,7 +24,7 @@ export function register(data: Record<string, any>) {
|
|||||||
method: 'post',
|
method: 'post',
|
||||||
data: data,
|
data: data,
|
||||||
whithToken: false,
|
whithToken: false,
|
||||||
crypto: true,
|
crypto: sessionGet(CACHE_SESSION_CRYPTO_API) !== 'false',
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -59,3 +61,69 @@ export function getCaptchaImage() {
|
|||||||
whithToken: false,
|
whithToken: false,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 登录认证源
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getLoginSource() {
|
||||||
|
return request({
|
||||||
|
url: '/auth/login/source',
|
||||||
|
method: 'GET',
|
||||||
|
whithToken: false,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* LDAP登录
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function loginLDAP(data: Record<string, string>) {
|
||||||
|
return request({
|
||||||
|
url: '/auth/login/ldap',
|
||||||
|
method: 'POST',
|
||||||
|
data: data,
|
||||||
|
whithToken: false,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* SMTP登录
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function loginSMTP(data: Record<string, string>) {
|
||||||
|
return request({
|
||||||
|
url: '/auth/login/smtp',
|
||||||
|
method: 'POST',
|
||||||
|
data: data,
|
||||||
|
whithToken: false,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 登录认证源OAuth2跳转登录URL
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function loginOAuth2URL(state: string): string {
|
||||||
|
// 兼容旧前端可改配置文件
|
||||||
|
const baseUrl = import.meta.env.PROD
|
||||||
|
? sessionGet('baseUrl') || import.meta.env.VITE_API_BASE_URL
|
||||||
|
: import.meta.env.VITE_API_BASE_URL;
|
||||||
|
return `${baseUrl}/auth/login/oauth2/authorize?state=${state}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 登录认证源OAuth2认证登录
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function loginOAuth2Token(code: string, state: string) {
|
||||||
|
return request({
|
||||||
|
url: '/auth/login/oauth2/token',
|
||||||
|
method: 'POST',
|
||||||
|
data: {
|
||||||
|
code,
|
||||||
|
state,
|
||||||
|
},
|
||||||
|
whithToken: false,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -5,10 +5,11 @@ import { request } from '@/plugins/http-fetch';
|
|||||||
* @param query 查询参数
|
* @param query 查询参数
|
||||||
* @returns object
|
* @returns object
|
||||||
*/
|
*/
|
||||||
export function getAllNeConfig(neType: string) {
|
export function getAllNeConfig(neType: string, neId: string) {
|
||||||
return request({
|
return request({
|
||||||
url: `/ne/config/list/${neType}`,
|
url: `/ne/config/list/${neType}`,
|
||||||
method: 'get',
|
method: 'get',
|
||||||
|
params: { neId },
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,3 +1,5 @@
|
|||||||
|
import { CACHE_SESSION_CRYPTO_API } from '@/constants/cache-keys-constants';
|
||||||
|
import { sessionGet } from '@/utils/cache-session-utils';
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -36,7 +38,7 @@ export function addNeInfo(data: Record<string, any>) {
|
|||||||
url: `/ne/info`,
|
url: `/ne/info`,
|
||||||
method: 'post',
|
method: 'post',
|
||||||
data: data,
|
data: data,
|
||||||
crypto: true,
|
crypto: sessionGet(CACHE_SESSION_CRYPTO_API) !== 'false',
|
||||||
timeout: 30_000,
|
timeout: 30_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -51,7 +53,7 @@ export function updateNeInfo(data: Record<string, any>) {
|
|||||||
url: `/ne/info`,
|
url: `/ne/info`,
|
||||||
method: 'put',
|
method: 'put',
|
||||||
data: data,
|
data: data,
|
||||||
crypto: true,
|
crypto: sessionGet(CACHE_SESSION_CRYPTO_API) !== 'false',
|
||||||
timeout: 30_000,
|
timeout: 30_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ export function listAMFDataUE(query: Record<string, any>) {
|
|||||||
url: '/neData/amf/ue/list',
|
url: '/neData/amf/ue/list',
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -37,6 +38,93 @@ export function exportAMFDataUE(data: Record<string, any>) {
|
|||||||
method: 'post',
|
method: 'post',
|
||||||
data,
|
data,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* AMF-接入基站信息列表
|
||||||
|
* @param query 查询参数 neId=001&id=1
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listAMFNblist(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/amf/nb/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* AMF-接入基站状态信息列表
|
||||||
|
* @param query 查询参数 neId=001&state=1
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listAMFNbStatelist(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/amf/nb/list-cfg',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* AMF-接入基站状态信息新增
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param data 数据 { "index": 1, "name": "Gnb", "address": "192.168.8.1", "position": "Area-B" }
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function addAMFNbState(neId: string, data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ne/config/data`,
|
||||||
|
method: 'post',
|
||||||
|
data: {
|
||||||
|
neType: 'AMF',
|
||||||
|
neId: neId,
|
||||||
|
paramName: 'gnbList',
|
||||||
|
paramData: data,
|
||||||
|
loc: `${data.index}`,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* AMF-接入基站状态信息修改
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param data 数据 { "index": 1, "name": "Gnb", "address": "192.168.8.1", "position": "Area-B" }
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function editAMFNbState(neId: string, data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ne/config/data`,
|
||||||
|
method: 'put',
|
||||||
|
data: {
|
||||||
|
neType: 'AMF',
|
||||||
|
neId: neId,
|
||||||
|
paramName: 'gnbList',
|
||||||
|
paramData: data,
|
||||||
|
loc: `${data.index}`,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* AMF-接入基站状态信息删除
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param index 数据index
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delAMFNbState(neId: string, index: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/ne/config/data`,
|
||||||
|
method: 'delete',
|
||||||
|
params: {
|
||||||
|
neType: 'AMF',
|
||||||
|
neId: neId,
|
||||||
|
paramName: 'gnbList',
|
||||||
|
loc: `${index}`,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -0,0 +1,68 @@
|
|||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 备份文件-获取FTP配置
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getBackupFTP() {
|
||||||
|
return request({
|
||||||
|
url: '/neData/backup/ftp',
|
||||||
|
method: 'GET',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 备份文件-文件FTP发送
|
||||||
|
* @param data 对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function pushBackupFTP(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/backup/ftp',
|
||||||
|
method: 'POST',
|
||||||
|
data,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 备份文件-更新FTP配置
|
||||||
|
* @param data 对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function updateBackupFTP(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/backup/ftp',
|
||||||
|
method: 'PUT',
|
||||||
|
data,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 备份文件-导出OMC
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function exportBackupOMC() {
|
||||||
|
return request({
|
||||||
|
url: '/neData/backup/export-omc',
|
||||||
|
method: 'POST',
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 备份文件-导入OMC
|
||||||
|
* @param filePath 备份文件上传返回的/upload 路径
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function importBackupOMC(filePath: string) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/backup/import-omc',
|
||||||
|
method: 'POST',
|
||||||
|
data: {
|
||||||
|
neType: 'OMC',
|
||||||
|
path: filePath,
|
||||||
|
},
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -10,6 +10,7 @@ export function listIMSDataCDR(query: Record<string, any>) {
|
|||||||
url: '/neData/ims/cdr/list',
|
url: '/neData/ims/cdr/list',
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -37,6 +38,6 @@ export function exportIMSDataCDR(data: Record<string, any>) {
|
|||||||
method: 'post',
|
method: 'post',
|
||||||
data,
|
data,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 60_000,
|
timeout: 180_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,148 @@
|
|||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户重载数据
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function resetIMSSub(neId: string) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/imsuser/resetData/${neId}`,
|
||||||
|
method: 'put',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户列表
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listIMSSub(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/ue/udm/imsuser/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
timeout: 30_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户信息
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param imsi IMSI
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getIMSSub(neId: string, imsi: string) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/imsuser/${neId}/${imsi}`,
|
||||||
|
method: 'get',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户新增
|
||||||
|
* @param data 签约对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function addIMSSub(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/imsuser/${data.neId}`,
|
||||||
|
method: 'post',
|
||||||
|
data: data,
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户批量新增
|
||||||
|
* @param data 签约对象
|
||||||
|
* @param num 数量
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function batchAddIMSSub(data: Record<string, any>, num: number) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/imsuser/${data.neId}/${num}`,
|
||||||
|
method: 'post',
|
||||||
|
data: data,
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户修改
|
||||||
|
* @param data 签约对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
// export function updateIMSSub(data: Record<string, any>) {
|
||||||
|
// return request({
|
||||||
|
// url: `/ue/udm/imsuser/${data.neId}`,
|
||||||
|
// method: 'put',
|
||||||
|
// data: data,
|
||||||
|
// timeout: 180_000,
|
||||||
|
// });
|
||||||
|
// }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户删除
|
||||||
|
* @param data 签约对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delIMSSub(neId: string, imsi_msisdn: string, tag: string) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/imsuser/${neId}/${imsi_msisdn}`,
|
||||||
|
method: 'delete',
|
||||||
|
params: { volte: tag },
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户批量删除
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param imsi IMSI
|
||||||
|
* @param num 数量
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function batchDelIMSSub(
|
||||||
|
neId: string,
|
||||||
|
imsi: string,
|
||||||
|
num: number,
|
||||||
|
tag: string
|
||||||
|
) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/imsuser/${neId}/${imsi}/${num}`,
|
||||||
|
method: 'delete',
|
||||||
|
params: { volte: tag },
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户导出
|
||||||
|
* @param data 数据参数
|
||||||
|
* @returns bolb
|
||||||
|
*/
|
||||||
|
export function exportIMSSub(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/ue/udm/imsuser/export',
|
||||||
|
method: 'post',
|
||||||
|
data,
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM签约用户导入
|
||||||
|
* @param data 表单数据对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function importIMSSub(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/imsuser/import`,
|
||||||
|
method: 'post',
|
||||||
|
data,
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -10,6 +10,7 @@ export function listMMEDataUE(query: Record<string, any>) {
|
|||||||
url: '/neData/mme/ue/list',
|
url: '/neData/mme/ue/list',
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -37,6 +38,93 @@ export function exportMMEDataUE(data: Record<string, any>) {
|
|||||||
method: 'post',
|
method: 'post',
|
||||||
data,
|
data,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* MME-接入基站信息列表
|
||||||
|
* @param query 查询参数 neId=001&id=1
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listMMENblist(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/mme/nb/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* MME-接入基站状态信息列表
|
||||||
|
* @param query 查询参数 neId=001&state=1
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listMMENbStatelist(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/mme/nb/list-cfg',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* MME-接入基站状态信息新增
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param data 数据 { "index": 1, "name": "Enb", "address": "192.168.8.1", "position": "Area-B" }
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function addMMENbState(neId: string, data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ne/config/data`,
|
||||||
|
method: 'post',
|
||||||
|
data: {
|
||||||
|
neType: 'MME',
|
||||||
|
neId: neId,
|
||||||
|
paramName: 'enbList',
|
||||||
|
paramData: data,
|
||||||
|
loc: `${data.index}`,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* MME-接入基站状态信息修改
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param data 数据 { "index": 1, "name": "Enb", "address": "192.168.8.1", "position": "Area-B" }
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function editMMENbState(neId: string, data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ne/config/data`,
|
||||||
|
method: 'put',
|
||||||
|
data: {
|
||||||
|
neType: 'MME',
|
||||||
|
neId: neId,
|
||||||
|
paramName: 'enbList',
|
||||||
|
paramData: data,
|
||||||
|
loc: `${data.index}`,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* MME-接入基站状态信息删除
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param index 数据index
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delMMENbState(neId: string, index: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/ne/config/data`,
|
||||||
|
method: 'delete',
|
||||||
|
params: {
|
||||||
|
neType: 'MME',
|
||||||
|
neId: neId,
|
||||||
|
paramName: 'enbList',
|
||||||
|
loc: `${index}`,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -0,0 +1,30 @@
|
|||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 历史记录列表
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listNBState(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/nb-state/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 历史记录列表导出
|
||||||
|
* @param data 查询列表条件
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function exportNBState(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/nb-state/export',
|
||||||
|
method: 'post',
|
||||||
|
data,
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -0,0 +1,43 @@
|
|||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询SGWC-CDR会话事件
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listSGWCDataCDR(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/sgwc/cdr/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* SGWC-CDR会话删除
|
||||||
|
* @param id 信息ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delSGWCDataCDR(cdrIds: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/neData/sgwc/cdr/${cdrIds}`,
|
||||||
|
method: 'delete',
|
||||||
|
timeout: 60_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* SGWC-CDR会话列表导出
|
||||||
|
* @param data 查询列表条件
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function exportSGWCDataCDR(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/sgwc/cdr/export',
|
||||||
|
method: 'post',
|
||||||
|
data,
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -10,6 +10,7 @@ export function listSMFDataCDR(query: Record<string, any>) {
|
|||||||
url: '/neData/smf/cdr/list',
|
url: '/neData/smf/cdr/list',
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -37,7 +38,20 @@ export function exportSMFDataCDR(data: Record<string, any>) {
|
|||||||
method: 'post',
|
method: 'post',
|
||||||
data,
|
data,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 60_000,
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* SMF-在线订阅用户数量
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listSMFSubNum(neId: string) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/smf/sub/num',
|
||||||
|
method: 'get',
|
||||||
|
params: { neId },
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -46,9 +60,9 @@ export function exportSMFDataCDR(data: Record<string, any>) {
|
|||||||
* @param query 查询参数
|
* @param query 查询参数
|
||||||
* @returns object
|
* @returns object
|
||||||
*/
|
*/
|
||||||
export function listSMFSubscribers(query: Record<string, any>) {
|
export function listSMFSubList(query: Record<string, any>) {
|
||||||
return request({
|
return request({
|
||||||
url: '/neData/smf/subscribers',
|
url: '/neData/smf/sub/list',
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ export function listSMSCDataCDR(query: Record<string, any>) {
|
|||||||
url: '/neData/smsc/cdr/list',
|
url: '/neData/smsc/cdr/list',
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -37,6 +38,6 @@ export function exportSMSCDataCDR(data: Record<string, any>) {
|
|||||||
method: 'post',
|
method: 'post',
|
||||||
data,
|
data,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 60_000,
|
timeout: 180_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -140,3 +140,17 @@ export function exportUDMAuth(data: Record<string, any>) {
|
|||||||
timeout: 180_000,
|
timeout: 180_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户导出DecAuth
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @returns bolb
|
||||||
|
*/
|
||||||
|
export function exportUDMDecAuth(neId: string) {
|
||||||
|
return request({
|
||||||
|
url: `/neData/udm/auth/export-dec?neId=${neId}`,
|
||||||
|
method: 'get',
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -0,0 +1,142 @@
|
|||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户重载数据
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function resetUDMAuth(neId: string) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/resetData/${neId}`,
|
||||||
|
method: 'put',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户列表
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listUDMAuth(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/ue/udm/voipauth/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
timeout: 30_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户信息
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param userName 用户名
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getUDMAuth(neId: string, userName: string) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/${neId}/${userName}`,
|
||||||
|
method: 'get',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户新增
|
||||||
|
* @param data 鉴权对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function addUDMAuth(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/${data.neId}`,
|
||||||
|
method: 'post',
|
||||||
|
data: data,
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户批量新增
|
||||||
|
* @param data 鉴权对象
|
||||||
|
* @param num 数量
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function batchAddUDMAuth(data: Record<string, any>, num: number) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/${data.neId}/${num}`,
|
||||||
|
method: 'post',
|
||||||
|
data: data,
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户修改
|
||||||
|
* @param data 鉴权对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function updateUDMAuth(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/${data.neId}`,
|
||||||
|
method: 'put',
|
||||||
|
data: data,
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户删除
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param imsi IMSI
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delUDMAuth(neId: string, imsi: string) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/${neId}/${imsi}`,
|
||||||
|
method: 'delete',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户批量删除
|
||||||
|
* @param neId 网元ID
|
||||||
|
* @param imsi IMSI
|
||||||
|
* @param num 数量
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function batchDelUDMAuth(neId: string, imsi: string, num: number) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/${neId}/${imsi}/${num}`,
|
||||||
|
method: 'delete',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户导入
|
||||||
|
* @param data 表单数据对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function importUDMAuth(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/udm/voipauth/import`,
|
||||||
|
method: 'post',
|
||||||
|
data,
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* UDM鉴权用户导出
|
||||||
|
* @param data 数据参数
|
||||||
|
* @returns bolb
|
||||||
|
*/
|
||||||
|
export function exportUDMAuth(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/ue/udm/voipauth/export',
|
||||||
|
method: 'post',
|
||||||
|
data,
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -0,0 +1,51 @@
|
|||||||
|
import { CACHE_SESSION_CRYPTO_API } from '@/constants/cache-keys-constants';
|
||||||
|
import { sessionGet } from '@/utils/cache-session-utils';
|
||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
/**
|
||||||
|
* 获取下拉框数据
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getBakFile() {
|
||||||
|
return request({
|
||||||
|
url: '/ue/table/list',
|
||||||
|
method: 'get',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* 获取对应类型的文件列表
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getBakFileList(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/ue/file/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* 下载远端文件
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function downFile(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/file/${query.fileName}`,
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 180_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* 删除远端获取文件
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delFile(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/ue/file/${query.fileName}`,
|
||||||
|
method: 'delete',
|
||||||
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -21,12 +21,14 @@ export async function listUEInfoBySMF(query: Record<string, any>) {
|
|||||||
};
|
};
|
||||||
// 解析数据
|
// 解析数据
|
||||||
if (result.code === RESULT_CODE_SUCCESS && result.data) {
|
if (result.code === RESULT_CODE_SUCCESS && result.data) {
|
||||||
if (Array.isArray(result.data.data)) {
|
if (result.data.total && result.data.data) {
|
||||||
const rows = result.data.data;
|
data.total = result.data.total;
|
||||||
data.total = rows.length;
|
data.rows = result.data.data;
|
||||||
data.rows = rows;
|
|
||||||
} else {
|
} else {
|
||||||
Object.assign(data, result.data);
|
Object.assign(data, {
|
||||||
|
total: result.data.length,
|
||||||
|
rows: result.data,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,7 +1,4 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 新 查询自定义指标数据
|
* 新 查询自定义指标数据
|
||||||
@@ -14,6 +11,7 @@ export async function listCustomData(query: Record<string, any>) {
|
|||||||
url: `/pm/kpiC/report`,
|
url: `/pm/kpiC/report`,
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
@@ -1,7 +1,4 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 查询自定义指标
|
* 查询自定义指标
|
||||||
|
|||||||
@@ -110,78 +110,52 @@ export async function getKPITitle(neType: string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Todo 废弃
|
* 查询黄金指标数据kpi.id转换title
|
||||||
* 查询UPF上下行速率数据
|
* @param neType 网元类型
|
||||||
* @param query 查询参数
|
|
||||||
* @returns object
|
* @returns object
|
||||||
*/
|
*/
|
||||||
export async function listUPFData(timeArr: any) {
|
export async function getKPITitleList(query: Record<string, any>) {
|
||||||
const initTime: Date = new Date();
|
return request({
|
||||||
const twentyFourHoursAgo: Date = new Date(
|
url: '/neData/kpi/title/list',
|
||||||
initTime.getTime() - 10 * 60 * 1000
|
method: 'get',
|
||||||
);
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
return await Promise.allSettled([
|
/**
|
||||||
// 获取参数规则
|
* 修改指标标题
|
||||||
request({
|
* @param data 指标标题对象
|
||||||
url: `/api/rest/databaseManagement/v1/select/omc_db/gold_kpi`,
|
* @returns object
|
||||||
method: 'get',
|
*/
|
||||||
params: {
|
export function updateKPITitle(data: Record<string, any>) {
|
||||||
SQL: `SELECT gold_kpi.*,kpi_title.en_title FROM gold_kpi LEFT JOIN kpi_title on gold_kpi.kpi_id=kpi_title.kpi_id where 1=1 and gold_kpi.kpi_id ='UPF.03' AND timestamp BETWEEN DATE_SUB(NOW(), INTERVAL 10 MINUTE) AND NOW()`,
|
return request({
|
||||||
},
|
url: '/neData/kpi/title',
|
||||||
timeout: 60_000,
|
method: 'put',
|
||||||
}),
|
data: data,
|
||||||
// 获取对应信息
|
});
|
||||||
request({
|
}
|
||||||
url: `/api/rest/databaseManagement/v1/select/omc_db/gold_kpi`,
|
//忙时呼叫
|
||||||
method: 'get',
|
export async function getbusyhour(query: Record<string, any>) {
|
||||||
params: {
|
return request({
|
||||||
SQL: `SELECT gold_kpi.*,kpi_title.en_title FROM gold_kpi LEFT JOIN kpi_title on gold_kpi.kpi_id=kpi_title.kpi_id where 1=1 and gold_kpi.kpi_id ='UPF.06' AND timestamp BETWEEN DATE_SUB(NOW(), INTERVAL 10 MINUTE) AND NOW()`,
|
url: '/neData/ims/kpi/busy-hour',
|
||||||
},
|
method: 'get',
|
||||||
timeout: 60_000,
|
params: query,
|
||||||
}),
|
});
|
||||||
]).then(resArr => {
|
}
|
||||||
let upData: any = [];
|
//MOS指标
|
||||||
let downData: any = [];
|
export async function getMosHour(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/neData/ims/cdr/mos-hour',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
// 规则数据
|
//CCT指标
|
||||||
if (resArr[0].status === 'fulfilled') {
|
export async function getCctHour(query: Record<string, any>) {
|
||||||
const itemV: any = resArr[0].value;
|
return request({
|
||||||
// 解析数据
|
url: '/neData/ims/cdr/cct-hour',
|
||||||
if (
|
method: 'get',
|
||||||
itemV.code === RESULT_CODE_SUCCESS &&
|
params: query,
|
||||||
Array.isArray(itemV.data?.data)
|
|
||||||
) {
|
|
||||||
let itemData = itemV.data.data;
|
|
||||||
let data = itemData[0]['gold_kpi'];
|
|
||||||
if (Array.isArray(data)) {
|
|
||||||
try {
|
|
||||||
upData = data.map(v => parseObjLineToHump(v));
|
|
||||||
} catch (error) {
|
|
||||||
console.error(error);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (resArr[1].status === 'fulfilled') {
|
|
||||||
const itemV = resArr[1].value;
|
|
||||||
// 解析数据
|
|
||||||
if (
|
|
||||||
itemV.code === RESULT_CODE_SUCCESS &&
|
|
||||||
Array.isArray(itemV.data?.data)
|
|
||||||
) {
|
|
||||||
let itemData = itemV.data.data;
|
|
||||||
const data = itemData[0]['gold_kpi'];
|
|
||||||
if (Array.isArray(data)) {
|
|
||||||
try {
|
|
||||||
downData = data.map(v => parseObjLineToHump(v));
|
|
||||||
} catch (error) {
|
|
||||||
console.error(error);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return { upData, downData };
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -1,7 +1,6 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
import { parseObjLineToHump } from '@/utils/parse-utils';
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 查询任务列表
|
* 查询任务列表
|
||||||
|
|||||||
@@ -0,0 +1,64 @@
|
|||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询登录源列表
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listLoginSource(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/system/login-source/list',
|
||||||
|
method: 'GET',
|
||||||
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询登录源详细
|
||||||
|
* @param id 登录源ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getLoginSource(id: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/system/login-source/${id}`,
|
||||||
|
method: 'GET',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 新增登录源
|
||||||
|
* @param data 登录源对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function addLoginSource(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/system/login-source',
|
||||||
|
method: 'POST',
|
||||||
|
data: data,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 修改登录源
|
||||||
|
* @param data 登录源对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function updateLoginSource(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/system/login-source',
|
||||||
|
method: 'PUT',
|
||||||
|
data: data,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 认证源删除
|
||||||
|
* @param id 登录源ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delLoginSource(id: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/system/login-source/${id}`,
|
||||||
|
method: 'DELETE',
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -0,0 +1,99 @@
|
|||||||
|
import { request } from '@/plugins/http-fetch';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询部门列表
|
||||||
|
* @param query 查询参数
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listTenant(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/system/tenant/list',
|
||||||
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询部门列表(排除节点)
|
||||||
|
* @param tenantId 部门ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function listTenantExcludeChild(tenantId: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/system/tenant/list/exclude/${tenantId}`,
|
||||||
|
method: 'get',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询部门详细
|
||||||
|
* @param tenantId 部门ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function getTenant(tenantId: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/system/tenant/${tenantId}`,
|
||||||
|
method: 'get',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 新增部门
|
||||||
|
* @param data 部门对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function addTenant(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/system/tenant',
|
||||||
|
method: 'post',
|
||||||
|
data: data,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 修改部门
|
||||||
|
* @param data 部门对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function updateTenant(data: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: '/system/tenant',
|
||||||
|
method: 'put',
|
||||||
|
data: data,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 删除部门
|
||||||
|
* @param TenantId 部门ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function delTenant(TenantId: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/system/tenant/${TenantId}`,
|
||||||
|
method: 'delete',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询部门下拉树结构
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function tenantTreeSelect() {
|
||||||
|
return request({
|
||||||
|
url: '/system/tenant/treeSelect',
|
||||||
|
method: 'get',
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 部门树结构列表(指定角色)
|
||||||
|
* @param roleId 角色ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function roleTenantTreeSelect(roleId: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/system/tenant/roleDeptTreeSelect/${roleId}`,
|
||||||
|
method: 'get',
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -15,7 +15,7 @@ import { encode } from 'js-base64';
|
|||||||
export async function downloadFile(filePath: string, range?: string) {
|
export async function downloadFile(filePath: string, range?: string) {
|
||||||
return request({
|
return request({
|
||||||
url: `/file/download/${encode(filePath)}`,
|
url: `/file/download/${encode(filePath)}`,
|
||||||
method: 'get',
|
method: 'GET',
|
||||||
headers: range ? { range } : {},
|
headers: range ? { range } : {},
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
@@ -76,8 +76,8 @@ export async function downloadFileChunk(
|
|||||||
*/
|
*/
|
||||||
export function uploadFile(data: FormData) {
|
export function uploadFile(data: FormData) {
|
||||||
return request({
|
return request({
|
||||||
url: '/file/upload',
|
url: '/file/upload2',
|
||||||
method: 'post',
|
method: 'POST',
|
||||||
data,
|
data,
|
||||||
dataType: 'form-data',
|
dataType: 'form-data',
|
||||||
timeout: 180_000,
|
timeout: 180_000,
|
||||||
@@ -169,7 +169,7 @@ export async function uploadFileChunk(
|
|||||||
export function chunkCheck(identifier: string, fileName: string) {
|
export function chunkCheck(identifier: string, fileName: string) {
|
||||||
return request({
|
return request({
|
||||||
url: '/file/chunkCheck',
|
url: '/file/chunkCheck',
|
||||||
method: 'post',
|
method: 'POST',
|
||||||
data: { identifier, fileName },
|
data: { identifier, fileName },
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
@@ -189,7 +189,7 @@ export function chunkMerge(
|
|||||||
) {
|
) {
|
||||||
return request({
|
return request({
|
||||||
url: '/file/chunkMerge',
|
url: '/file/chunkMerge',
|
||||||
method: 'post',
|
method: 'POST',
|
||||||
data: { identifier, fileName, subPath },
|
data: { identifier, fileName, subPath },
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
@@ -203,13 +203,57 @@ export function chunkMerge(
|
|||||||
export function chunkUpload(data: FormData) {
|
export function chunkUpload(data: FormData) {
|
||||||
return request({
|
return request({
|
||||||
url: '/file/chunkUpload',
|
url: '/file/chunkUpload',
|
||||||
method: 'post',
|
method: 'POST',
|
||||||
data,
|
data,
|
||||||
dataType: 'form-data',
|
dataType: 'form-data',
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 本地文件列表
|
||||||
|
* @param path 文件路径
|
||||||
|
* @param search search prefix
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export async function listFile(query: Record<string, any>) {
|
||||||
|
return request({
|
||||||
|
url: `/file/list`,
|
||||||
|
method: 'GET',
|
||||||
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 本地文件获取下载
|
||||||
|
* @param path 文件路径
|
||||||
|
* @param fileName 文件名
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export async function getFile(path: string, fileName: string) {
|
||||||
|
return request({
|
||||||
|
url: `/file`,
|
||||||
|
method: 'GET',
|
||||||
|
params: { path, fileName },
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 60_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 本地文件删除
|
||||||
|
* @param path 文件路径
|
||||||
|
* @param fileName 文件名
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export async function delFile(path: string, fileName: string) {
|
||||||
|
return request({
|
||||||
|
url: `/file`,
|
||||||
|
method: 'DELETE',
|
||||||
|
params: { path, fileName },
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 转存上传文件到静态资源
|
* 转存上传文件到静态资源
|
||||||
* @returns object
|
* @returns object
|
||||||
@@ -217,7 +261,7 @@ export function chunkUpload(data: FormData) {
|
|||||||
export function transferStaticFile(data: Record<string, any>) {
|
export function transferStaticFile(data: Record<string, any>) {
|
||||||
return request({
|
return request({
|
||||||
url: `/file/transferStaticFile`,
|
url: `/file/transferStaticFile`,
|
||||||
method: 'post',
|
method: 'POST',
|
||||||
data,
|
data,
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
@@ -241,11 +285,12 @@ export async function uploadFileToNE(
|
|||||||
if (uploadChunkRes.code === RESULT_CODE_SUCCESS) {
|
if (uploadChunkRes.code === RESULT_CODE_SUCCESS) {
|
||||||
const transferToNeFileRes = await request({
|
const transferToNeFileRes = await request({
|
||||||
url: `/ne/action/pushFile`,
|
url: `/ne/action/pushFile`,
|
||||||
method: 'post',
|
method: 'POST',
|
||||||
data: {
|
data: {
|
||||||
uploadPath: uploadChunkRes.data.fileName,
|
uploadPath: uploadChunkRes.data.fileName,
|
||||||
neType,
|
neType,
|
||||||
neId,
|
neId,
|
||||||
|
delTemp: true,
|
||||||
},
|
},
|
||||||
timeout: 60_000,
|
timeout: 60_000,
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ export function getNeFile(query: Record<string, any>) {
|
|||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 180_000,
|
timeout: 600_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -35,7 +35,7 @@ export function getNeDirZip(data: Record<string, any>) {
|
|||||||
method: 'get',
|
method: 'get',
|
||||||
params: data,
|
params: data,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 60_000,
|
timeout: 600_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -45,6 +45,6 @@ export function getNeViewFile(data: Record<string, any>) {
|
|||||||
url: '/ne/action/viewFile',
|
url: '/ne/action/viewFile',
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: data,
|
params: data,
|
||||||
timeout: 60_000,
|
timeout: 600_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@@ -8,3 +8,12 @@ export function pingV(data: Record<string, string>) {
|
|||||||
params: data,
|
params: data,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ping RTT 时延抖动
|
||||||
|
export function pingRTT(data: Record<string, string>) {
|
||||||
|
return request({
|
||||||
|
url: '/tool/ping/rtt',
|
||||||
|
method: 'POST',
|
||||||
|
data: data,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -1,71 +0,0 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
|
||||||
import { request } from '@/plugins/http-fetch';
|
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 查询信令列表
|
|
||||||
* @param query 查询参数
|
|
||||||
* @returns object
|
|
||||||
*/
|
|
||||||
export async function listTraceData(query: Record<string, any>) {
|
|
||||||
let totalSQL = 'select count(*) as total from trace_data where 1=1 ';
|
|
||||||
let rowsSQL = 'select * from trace_data where 1=1 ';
|
|
||||||
|
|
||||||
// 查询
|
|
||||||
let querySQL = '';
|
|
||||||
if (query.imsi) {
|
|
||||||
querySQL += ` and imsi like '%${query.imsi}%' `;
|
|
||||||
}
|
|
||||||
if (query.msisdn) {
|
|
||||||
querySQL += ` and msisdn like '%${query.msisdn}%' `;
|
|
||||||
}
|
|
||||||
|
|
||||||
// 分页
|
|
||||||
const pageNum = (query.pageNum - 1) * query.pageSize;
|
|
||||||
const limtSql = ` limit ${pageNum},${query.pageSize} `;
|
|
||||||
|
|
||||||
// 发起请求
|
|
||||||
const result = await request({
|
|
||||||
url: `/api/rest/databaseManagement/v1/omc_db/trace_data`,
|
|
||||||
method: 'get',
|
|
||||||
params: {
|
|
||||||
totalSQL: totalSQL + querySQL,
|
|
||||||
rowsSQL: rowsSQL + querySQL + limtSql,
|
|
||||||
},
|
|
||||||
});
|
|
||||||
|
|
||||||
// 解析数据
|
|
||||||
if (result.code === RESULT_CODE_SUCCESS) {
|
|
||||||
const data: DataList = {
|
|
||||||
total: 0,
|
|
||||||
rows: [],
|
|
||||||
code: result.code,
|
|
||||||
msg: result.msg,
|
|
||||||
};
|
|
||||||
result.data.data.forEach((item: any) => {
|
|
||||||
const itemData = item['trace_data'];
|
|
||||||
if (Array.isArray(itemData)) {
|
|
||||||
if (itemData.length === 1 && itemData[0]['total'] >= 0) {
|
|
||||||
data.total = itemData[0]['total'];
|
|
||||||
} else {
|
|
||||||
data.rows = itemData.map(v => parseObjLineToHump(v));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
return data;
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* 信令数据解析HTML
|
|
||||||
* @param id 任务ID
|
|
||||||
* @returns
|
|
||||||
*/
|
|
||||||
export function getTraceRawInfo(id: Record<string, string>) {
|
|
||||||
return request({
|
|
||||||
url: `/api/rest/traceManagement/v1/decMessage/${id}`,
|
|
||||||
method: 'get',
|
|
||||||
responseType: 'text',
|
|
||||||
});
|
|
||||||
}
|
|
||||||
@@ -62,3 +62,18 @@ export function packetKeep(taskNo: string, duration: number = 120) {
|
|||||||
data: { taskNo, duration },
|
data: { taskNo, duration },
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 信令跟踪文件
|
||||||
|
* @param taskNo 对象
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export function packetPCAPFile(taskNo: string) {
|
||||||
|
return request({
|
||||||
|
url: '/trace/packet/filePull',
|
||||||
|
method: 'get',
|
||||||
|
params: { taskNo },
|
||||||
|
responseType: 'blob',
|
||||||
|
timeout: 680_000,
|
||||||
|
});
|
||||||
|
}
|
||||||
@@ -1,6 +1,4 @@
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
|
||||||
import { request } from '@/plugins/http-fetch';
|
import { request } from '@/plugins/http-fetch';
|
||||||
import { parseObjLineToHump } from '@/utils/parse-utils';
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 查询跟踪任务列表
|
* 查询跟踪任务列表
|
||||||
@@ -76,29 +74,31 @@ export function filePullTask(traceId: string) {
|
|||||||
method: 'get',
|
method: 'get',
|
||||||
params: { traceId },
|
params: { traceId },
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 60_000,
|
timeout: 600_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 获取网元跟踪接口列表
|
* 跟踪任务数据列表
|
||||||
|
* @param query 查询参数
|
||||||
* @returns object
|
* @returns object
|
||||||
*/
|
*/
|
||||||
export async function getNeTraceInterfaceAll() {
|
export async function listTraceData(query: Record<string, any>) {
|
||||||
// 发起请求
|
return request({
|
||||||
const result = await request({
|
url: '/trace/data/list',
|
||||||
url: `/api/rest/databaseManagement/v1/elementType/omc_db/objectType/ne_info`,
|
method: 'get',
|
||||||
|
params: query,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 查询跟踪任务数据信息
|
||||||
|
* @param id ID
|
||||||
|
* @returns object
|
||||||
|
*/
|
||||||
|
export async function getTraceData(id: string | number) {
|
||||||
|
return request({
|
||||||
|
url: `/trace/data/${id}`,
|
||||||
method: 'get',
|
method: 'get',
|
||||||
params: {
|
|
||||||
SQL: `SELECT ne_type,interface FROM trace_info GROUP BY ne_type,interface`,
|
|
||||||
},
|
|
||||||
});
|
});
|
||||||
// 解析数据
|
|
||||||
if (result.code === RESULT_CODE_SUCCESS && Array.isArray(result.data.data)) {
|
|
||||||
let data = result.data.data[0];
|
|
||||||
return Object.assign(result, {
|
|
||||||
data: parseObjLineToHump(data['trace_info']),
|
|
||||||
});
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
}
|
||||||
@@ -78,6 +78,6 @@ export function filePullTaskHLR(query: Record<string, any>) {
|
|||||||
method: 'get',
|
method: 'get',
|
||||||
params: query,
|
params: query,
|
||||||
responseType: 'blob',
|
responseType: 'blob',
|
||||||
timeout: 60_000,
|
timeout: 600_000,
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
Before Width: | Height: | Size: 226 KiB |
|
Before Width: | Height: | Size: 70 KiB |
@@ -0,0 +1 @@
|
|||||||
|
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1721721606045" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="7339" width="200" height="200"><path d="M610.6 234.24L627 294.6c90.88-24.73 184.58 28.77 209.45 119.65l60.36-16.4C862.92 273.5 734.67 200.37 610.6 234.24z m-34.42-126.22l16.4 60.36c160.51-43.83 326.13 50.81 369.96 211.33l60.36-16.4C969.94 169.45 770.03 55.18 576.18 108.02zM179.47 922.27V827.5H0v-84.83l179.47-261.74h92.22v274.24h62.38v72.33h-62.38v94.77h-92.22z m0-167.09V598.02L72.33 755.18h107.14z m0 0" p-id="7340" fill="#ffffff"></path><path d="M695.69 752.62h-89.8v-77.29h186.99v231.9c-33.34 9.95-67.35 14.92-102.17 14.92-26.62 3.37-61.57 4.97-104.72 4.97-141.29-8.33-213.62-86.44-216.97-234.31 3.36-151.24 75.69-231.9 216.97-241.85 144.65 0 216.03 49.88 214.42 149.63H695.69c0-51.49-30.79-77.3-92.23-77.3-84.83 1.62-127.98 58.21-129.59 169.52 1.61 109.7 44.9 165.49 129.59 167.1 24.87 0 54.05-3.36 87.25-9.95-1.61 1.61 0 1.61 4.98 0v-97.34z m0 0" p-id="7341" fill="#ffffff"></path></svg>
|
||||||
|
After Width: | Height: | Size: 1.1 KiB |
@@ -0,0 +1 @@
|
|||||||
|
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1721721630123" class="icon" viewBox="0 0 1216 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="54141" width="200" height="200"><path d="M747.264 190.912l18.368 67.328a190.272 190.272 0 0 1 233.728 133.44l67.264-18.368a260.032 260.032 0 0 0-319.36-182.4z m-38.4-140.736l18.368 67.328a336.192 336.192 0 0 1 412.8 235.776l67.328-18.368A405.952 405.952 0 0 0 708.864 50.176z m133.376 719.232h-100.16v-86.272h208.64v258.752c-37.12 11.136-75.072 16.704-114.048 16.704a984.96 984.96 0 0 1-116.864 5.568c-157.632-9.28-238.336-96.448-242.048-261.504 3.712-168.768 84.416-258.752 242.048-269.888 161.344 0 241.088 55.68 239.296 166.912H842.24c0-57.472-34.368-86.208-102.912-86.208-94.592 1.856-142.848 64.896-144.64 189.184 1.792 122.368 50.048 184.576 144.64 186.368 27.776 0 60.16-3.712 97.344-11.136-1.92 1.92 0 1.92 5.568 0v-108.48zM234.24 969.216c-86.016 0-148.992-30.72-201.216-80.64l71.424-85.248c40.704 36.864 80.64 58.368 128.256 58.368 55.296 0 89.856-26.88 89.856-74.496v-1.536c0-46.08-39.168-72.96-95.232-72.96-33.792 0-64.512 9.216-89.856 19.968L69.12 687.36l15.36-264.96h330.24v103.68H185.856l-6.144 92.928a262.976 262.976 0 0 1 70.656-9.216c104.448 0 188.16 50.688 188.16 172.032v1.536c0 113.664-80.64 185.856-204.288 185.856z" p-id="54142" fill="#ffffff"></path></svg>
|
||||||
|
After Width: | Height: | Size: 1.4 KiB |
@@ -0,0 +1,3 @@
|
|||||||
|
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1720074329868" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="4280" width="64" height="64"><path d="M616.5 151.3l-28.3 28.3c19.7 19.6 31.8 46.6 31.8 76.5 0 29.8-12.2 56.9-31.8 76.5l28.3 28.3c26.8-27 43.5-64 43.5-104.9s-16.7-77.9-43.5-104.7zM435.8 179.5l-28.3-28.3C380.7 178.1 364 215.1 364 256s16.7 77.9 43.5 104.7l28.3-28.3C416.2 312.9 404 285.8 404 256c0-29.9 12.2-56.9 31.8-76.5zM346.6 134.3L318.3 106c-38.5 38.4-62.3 91.5-62.3 150s23.8 111.6 62.3 150l28.3-28.3C315.3 346.6 296 303.5 296 256s19.3-90.6 50.6-121.7zM705.7 106l-28.3 28.3C708.7 165.4 728 208.5 728 256s-19.3 90.6-50.6 121.7l28.3 28.3c38.5-38.4 62.3-91.5 62.3-150s-23.8-111.6-62.3-150zM815.2 60.8l-0.1-0.1L786.7 89c0.1 0 0.1 0.1 0.2 0.1C831.5 133.7 856 193 856 256s-24.5 122.3-69.1 166.9c0 0-0.1 0.1-0.2 0.1l28.3 28.3 0.1-0.1C867.3 399 896 329.7 896 256s-28.7-143-80.8-195.2zM237.3 89L209 60.7l-0.1 0.1C156.7 113 128 182.3 128 256s28.7 143 80.8 195.2l0.1 0.1 28.3-28.3c-0.1 0-0.1-0.1-0.2-0.1-44.5-44.6-69-103.9-69-166.9s24.5-122.3 69.1-166.9c0.1 0 0.1-0.1 0.2-0.1zM511.712 256.002l0.283-0.283 0.283 0.283-0.283 0.283z" p-id="4281" fill="#ffffff"></path><path d="M511.719 256.021l0.282-0.282 0.283 0.282-0.283 0.283z" p-id="4282" fill="#ffffff"></path><path d="M708.4 616l-14.2-26.1-7.6-13.9-11.6-21.2L512 256 337.5 576l-21.8 40L128 960h74l33.8-64 28.9-53h494.6l28.9 53 33.8 64h74L708.4 616zM512 389.6L613.7 576H410.3L512 389.6zM388.5 616H569L305.6 768.1 388.5 616z m-63.4 187l313.6-181.1L737.5 803H325.1z" p-id="4283" fill="#ffffff"></path></svg>
|
||||||
|
|
||||||
|
|
||||||
|
After Width: | Height: | Size: 1.7 KiB |
@@ -0,0 +1 @@
|
|||||||
|
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1729046804258" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1511" width="200" height="200"><path d="M958.359001 286.941198c0-64.308655-52.132334-116.440989-116.440989-116.440989L181.453678 170.500209c-64.308655 0-116.440989 52.132334-116.440989 116.440989l0 448.63995c0 64.308655 52.132334 116.440989 116.440989 116.440989l660.464333 0c64.308655 0 116.440989-52.132334 116.440989-116.440989L958.359001 286.941198zM843.814198 212.455763c12.059664 0 23.444968 3.465938 33.519418 8.598842L530.749016 549.347606c-1.227967 1.161453-1.156336 0.916882-1.752924 1.868557-1.426489 1.067308-6.055926 3.922333-15.449877 3.922333-9.397021 0-14.025435-2.75474-15.4509-3.818979-0.676405-1.077541-0.662079-0.716314-1.995447-1.940189l-353.122503-324.412624c11.609409-7.557116 25.445532-12.509918 40.300868-12.509918L843.814198 212.456786zM916.403446 736.484727c0 40.857547-31.730679 73.582879-72.589248 73.582879L183.27721 810.067606c-40.85857 0-75.28566-32.725332-75.28566-73.582879L107.99155 287.657512c0-10.630105 2.860141-20.735253 6.909363-29.882588l351.486236 322.096882c4.91187 5.302773 19.479657 17.676591 47.009663 17.676591 27.799136 0 42.303478-12.618389 47.076178-17.830087l346.800517-328.899822c6.251378 10.860349 9.129938 23.433712 9.129938 36.838L916.403446 736.484727z" fill="#ffffff" p-id="1512"></path></svg>
|
||||||
|
After Width: | Height: | Size: 1.5 KiB |
@@ -0,0 +1,479 @@
|
|||||||
|
<template>
|
||||||
|
<a-modal
|
||||||
|
v-model:open="visible"
|
||||||
|
:title="t('common.exportCustom')"
|
||||||
|
width="750px"
|
||||||
|
:confirm-loading="confirmLoading"
|
||||||
|
@ok="handleOk"
|
||||||
|
@cancel="handleCancel"
|
||||||
|
>
|
||||||
|
<div class="export-custom-container">
|
||||||
|
<!-- 列配置区域 -->
|
||||||
|
<div class="columns-config">
|
||||||
|
<div class="config-header">
|
||||||
|
<h4>{{ t('common.exportColumns') }}</h4>
|
||||||
|
<a-button type="link" @click="resetToDefault">
|
||||||
|
{{ t('common.resetToDefault') }}
|
||||||
|
</a-button>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="columns-list">
|
||||||
|
<Container
|
||||||
|
@drop="onDrop"
|
||||||
|
:get-child-payload="getChildPayload"
|
||||||
|
drag-class="drag-ghost"
|
||||||
|
drop-class="drop-ghost"
|
||||||
|
drag-handle-selector=".drag-handle"
|
||||||
|
:non-drag-area-selector="'.column-name, .ant-checkbox-wrapper'"
|
||||||
|
>
|
||||||
|
<Draggable
|
||||||
|
v-for="(column, index) in customColumns"
|
||||||
|
:key="column.key"
|
||||||
|
class="column-item"
|
||||||
|
>
|
||||||
|
<div class="column-controls">
|
||||||
|
<a-checkbox
|
||||||
|
v-model:checked="column.visible"
|
||||||
|
@change="updateColumnVisibility(column)"
|
||||||
|
/>
|
||||||
|
<div class="drag-handle">
|
||||||
|
<HolderOutlined />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="column-info">
|
||||||
|
<div class="column-name">
|
||||||
|
<a-input
|
||||||
|
v-model:value="column.title"
|
||||||
|
:placeholder="t('common.columnName')"
|
||||||
|
size="small"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<!-- 隐藏col_数字标签,不影响用户使用 -->
|
||||||
|
<!-- <div class="column-key">
|
||||||
|
<a-tag size="small" color="blue">{{ column.key }}</a-tag>
|
||||||
|
</div> -->
|
||||||
|
</div>
|
||||||
|
</Draggable>
|
||||||
|
</Container>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- 预览区域 -->
|
||||||
|
<div class="preview-section">
|
||||||
|
<h4>{{ t('common.preview') }}</h4>
|
||||||
|
<div class="preview-table">
|
||||||
|
<a-table
|
||||||
|
:columns="previewColumns"
|
||||||
|
:data-source="previewData"
|
||||||
|
:pagination="false"
|
||||||
|
size="small"
|
||||||
|
:scroll="{ x: 400 }"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</a-modal>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
import { ref, computed, watch, onMounted } from 'vue';
|
||||||
|
import { Modal, message } from 'ant-design-vue/es';
|
||||||
|
import { Container, Draggable } from 'vue3-smooth-dnd';
|
||||||
|
import useI18n from '@/hooks/useI18n';
|
||||||
|
import { ColumnsType } from 'ant-design-vue/es/table';
|
||||||
|
|
||||||
|
interface CustomColumn {
|
||||||
|
key: string;
|
||||||
|
title: string;
|
||||||
|
visible: boolean;
|
||||||
|
originalTitle: string;
|
||||||
|
dataIndex?: string;
|
||||||
|
customRender?: any;
|
||||||
|
columnIndex?: number; // Excel列索引
|
||||||
|
}
|
||||||
|
|
||||||
|
interface Props {
|
||||||
|
open: boolean;
|
||||||
|
originalColumns: ColumnsType;
|
||||||
|
sampleData: any[];
|
||||||
|
}
|
||||||
|
|
||||||
|
interface Emits {
|
||||||
|
(e: 'update:open', value: boolean): void;
|
||||||
|
(e: 'confirm', config: CustomColumn[]): void;
|
||||||
|
}
|
||||||
|
|
||||||
|
const props = defineProps<Props>();
|
||||||
|
const emit = defineEmits<Emits>();
|
||||||
|
const { t } = useI18n();
|
||||||
|
|
||||||
|
const visible = ref(false);
|
||||||
|
const confirmLoading = ref(false);
|
||||||
|
const customColumns = ref<CustomColumn[]>([]);
|
||||||
|
|
||||||
|
// 监听props变化
|
||||||
|
watch(() => props.open, (newVal) => {
|
||||||
|
visible.value = newVal;
|
||||||
|
if (newVal) {
|
||||||
|
initCustomColumns();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
watch(visible, (newVal) => {
|
||||||
|
emit('update:open', newVal);
|
||||||
|
});
|
||||||
|
|
||||||
|
// 初始化自定义列配置
|
||||||
|
function initCustomColumns() {
|
||||||
|
// 如果传入的是完整的列配置(包含columnIndex),直接使用
|
||||||
|
if (props.originalColumns.length > 0 && (props.originalColumns[0] as any).columnIndex !== undefined) {
|
||||||
|
const columns: CustomColumn[] = props.originalColumns.map(col => ({
|
||||||
|
key: (col as any).key,
|
||||||
|
title: (col as any).title,
|
||||||
|
visible: true,
|
||||||
|
originalTitle: (col as any).originalTitle || (col as any).title,
|
||||||
|
dataIndex: (col as any).dataIndex,
|
||||||
|
columnIndex: (col as any).columnIndex
|
||||||
|
}));
|
||||||
|
|
||||||
|
// 尝试从本地存储加载配置
|
||||||
|
const savedConfig = localStorage.getItem('sgwc-cdr-export-config');
|
||||||
|
if (savedConfig) {
|
||||||
|
try {
|
||||||
|
const saved = JSON.parse(savedConfig);
|
||||||
|
console.log('Loaded saved config:', saved);
|
||||||
|
|
||||||
|
// 基于originalTitle匹配保存的配置
|
||||||
|
const mergedColumns = columns.map(col => {
|
||||||
|
const savedCol = saved.find((s: any) => s.originalTitle === col.originalTitle);
|
||||||
|
if (savedCol) {
|
||||||
|
console.log(`Matched column: ${col.originalTitle}, visible: ${savedCol.visible}, title: ${savedCol.title}`);
|
||||||
|
return {
|
||||||
|
...col,
|
||||||
|
visible: savedCol.visible !== undefined ? savedCol.visible : true,
|
||||||
|
title: savedCol.title || col.title
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return col;
|
||||||
|
});
|
||||||
|
|
||||||
|
// 按照保存的顺序排列(如果存在)
|
||||||
|
const sortedColumns = sortColumnsByConfig(mergedColumns, saved);
|
||||||
|
console.log('Final columns after merge and sort:', sortedColumns);
|
||||||
|
customColumns.value = sortedColumns;
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Failed to load saved export config:', error);
|
||||||
|
customColumns.value = columns;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
console.log('No saved config found, using default columns');
|
||||||
|
customColumns.value = columns;
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 兼容旧的表格列配置
|
||||||
|
const columns: CustomColumn[] = props.originalColumns
|
||||||
|
.filter(col => col.key !== 'id' && (col as any).dataIndex) // 过滤掉操作列
|
||||||
|
.map(col => ({
|
||||||
|
key: col.key as string,
|
||||||
|
title: col.title as string,
|
||||||
|
visible: true,
|
||||||
|
originalTitle: col.title as string,
|
||||||
|
dataIndex: (col as any).dataIndex as string,
|
||||||
|
customRender: (col as any).customRender
|
||||||
|
}));
|
||||||
|
|
||||||
|
// 尝试从本地存储加载配置
|
||||||
|
const savedConfig = localStorage.getItem('sgwc-cdr-export-config');
|
||||||
|
if (savedConfig) {
|
||||||
|
try {
|
||||||
|
const saved = JSON.parse(savedConfig);
|
||||||
|
// 合并保存的配置和当前列,只合并特定字段
|
||||||
|
const mergedColumns = columns.map(col => {
|
||||||
|
const savedCol = saved.find((s: CustomColumn) => s.key === col.key);
|
||||||
|
if (savedCol) {
|
||||||
|
return {
|
||||||
|
...col,
|
||||||
|
visible: savedCol.visible, // 只合并可见性
|
||||||
|
title: savedCol.title !== savedCol.originalTitle ? savedCol.title : col.title // 只合并自定义的标题
|
||||||
|
};
|
||||||
|
}
|
||||||
|
return col;
|
||||||
|
});
|
||||||
|
customColumns.value = mergedColumns;
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Failed to load saved export config:', error);
|
||||||
|
customColumns.value = columns;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
customColumns.value = columns;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 按照保存的配置排序列
|
||||||
|
function sortColumnsByConfig(columns: CustomColumn[], savedConfig: CustomColumn[]): CustomColumn[] {
|
||||||
|
if (!savedConfig || savedConfig.length === 0) {
|
||||||
|
return columns;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 创建一个映射:originalTitle -> savedOrder
|
||||||
|
const orderMap = new Map<string, number>();
|
||||||
|
savedConfig.forEach((col, index) => {
|
||||||
|
orderMap.set(col.originalTitle, index);
|
||||||
|
});
|
||||||
|
|
||||||
|
// 排序:已保存的列按保存顺序,新列放在最后
|
||||||
|
return [...columns].sort((a, b) => {
|
||||||
|
const orderA = orderMap.has(a.originalTitle) ? orderMap.get(a.originalTitle)! : 9999;
|
||||||
|
const orderB = orderMap.has(b.originalTitle) ? orderMap.get(b.originalTitle)! : 9999;
|
||||||
|
return orderA - orderB;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 预览列配置
|
||||||
|
const previewColumns = computed(() => {
|
||||||
|
return customColumns.value
|
||||||
|
.filter(col => col.visible)
|
||||||
|
.map(col => ({
|
||||||
|
title: col.title,
|
||||||
|
dataIndex: col.dataIndex || col.key,
|
||||||
|
key: col.key,
|
||||||
|
customRender: col.customRender
|
||||||
|
}));
|
||||||
|
});
|
||||||
|
|
||||||
|
// 预览数据(只显示前2条,降低预览高度)
|
||||||
|
const previewData = computed(() => {
|
||||||
|
return props.sampleData.slice(0, 1);
|
||||||
|
});
|
||||||
|
|
||||||
|
// 更新列可见性
|
||||||
|
function updateColumnVisibility(column: CustomColumn) {
|
||||||
|
// 确保至少有一列可见
|
||||||
|
const visibleCount = customColumns.value.filter(col => col.visible).length;
|
||||||
|
if (visibleCount === 0) {
|
||||||
|
column.visible = true;
|
||||||
|
message.warning(t('common.atLeastOneColumn'));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 拖拽相关函数
|
||||||
|
function getChildPayload(index: number) {
|
||||||
|
return customColumns.value[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
function onDrop(dropResult: any) {
|
||||||
|
const { removedIndex, addedIndex } = dropResult;
|
||||||
|
if (removedIndex !== null && addedIndex !== null) {
|
||||||
|
const item = customColumns.value[removedIndex];
|
||||||
|
customColumns.value.splice(removedIndex, 1);
|
||||||
|
customColumns.value.splice(addedIndex, 0, item);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 重置为默认配置
|
||||||
|
function resetToDefault() {
|
||||||
|
Modal.confirm({
|
||||||
|
title: t('common.confirm'),
|
||||||
|
content: t('common.resetConfirm'),
|
||||||
|
onOk() {
|
||||||
|
// 清除本地存储的配置
|
||||||
|
localStorage.removeItem('sgwc-cdr-export-config');
|
||||||
|
// 重新初始化
|
||||||
|
initCustomColumns();
|
||||||
|
message.success(t('common.resetSuccess'));
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 确认导出
|
||||||
|
function handleOk() {
|
||||||
|
const visibleColumns = customColumns.value.filter(col => col.visible);
|
||||||
|
if (visibleColumns.length === 0) {
|
||||||
|
message.error(t('common.selectAtLeastOneColumn'));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
confirmLoading.value = true;
|
||||||
|
|
||||||
|
// 保存配置到本地存储
|
||||||
|
try {
|
||||||
|
// 保存时只保存必要的字段,用于下次加载时恢复配置
|
||||||
|
const configToSave = customColumns.value.map((col, index) => ({
|
||||||
|
originalTitle: col.originalTitle || col.title, // 用于匹配列
|
||||||
|
title: col.title, // 自定义标题
|
||||||
|
visible: col.visible, // 可见性
|
||||||
|
order: index // 顺序
|
||||||
|
}));
|
||||||
|
localStorage.setItem('sgwc-cdr-export-config', JSON.stringify(configToSave));
|
||||||
|
console.log('Export config saved:', configToSave);
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Failed to save export config:', error);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 延迟一下让用户看到loading状态
|
||||||
|
setTimeout(() => {
|
||||||
|
emit('confirm', customColumns.value);
|
||||||
|
confirmLoading.value = false;
|
||||||
|
visible.value = false;
|
||||||
|
}, 500);
|
||||||
|
}
|
||||||
|
|
||||||
|
// 取消
|
||||||
|
function handleCancel() {
|
||||||
|
visible.value = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
onMounted(() => {
|
||||||
|
if (props.open) {
|
||||||
|
initCustomColumns();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// 调试功能:清除有问题的缓存
|
||||||
|
function clearProblematicCache() {
|
||||||
|
localStorage.removeItem('sgwc-cdr-export-config');
|
||||||
|
console.log('Cleared problematic cache');
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style lang="less" scoped>
|
||||||
|
.export-custom-container {
|
||||||
|
.columns-config {
|
||||||
|
margin-bottom: 12px;
|
||||||
|
|
||||||
|
.config-header {
|
||||||
|
display: flex;
|
||||||
|
justify-content: space-between;
|
||||||
|
align-items: center;
|
||||||
|
margin-bottom: 10px;
|
||||||
|
|
||||||
|
h4 {
|
||||||
|
margin: 0;
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 600;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.columns-list {
|
||||||
|
border: 1px solid #d9d9d9;
|
||||||
|
border-radius: 6px;
|
||||||
|
max-height: 200px;
|
||||||
|
overflow-y: auto;
|
||||||
|
|
||||||
|
.column-item {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
padding: 6px 10px;
|
||||||
|
border-bottom: 1px solid #f0f0f0;
|
||||||
|
transition: background-color 0.2s;
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
background-color: #fafafa;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:last-child {
|
||||||
|
border-bottom: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.column-controls {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
margin-right: 12px;
|
||||||
|
|
||||||
|
.drag-handle {
|
||||||
|
margin-left: 8px;
|
||||||
|
cursor: grab;
|
||||||
|
color: #999;
|
||||||
|
padding: 4px;
|
||||||
|
border-radius: 4px;
|
||||||
|
transition: all 0.2s;
|
||||||
|
user-select: none;
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
color: #1890ff;
|
||||||
|
background-color: #f0f0f0;
|
||||||
|
}
|
||||||
|
|
||||||
|
&:active {
|
||||||
|
cursor: grabbing;
|
||||||
|
color: #0050b3;
|
||||||
|
background-color: #e6f7ff;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.column-info {
|
||||||
|
flex: 1;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
pointer-events: auto;
|
||||||
|
cursor: default;
|
||||||
|
|
||||||
|
.column-name {
|
||||||
|
flex: 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
.column-key {
|
||||||
|
display: none; // 隐藏标签
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 禁止复选框触发拖拽
|
||||||
|
:deep(.ant-checkbox-wrapper) {
|
||||||
|
pointer-events: auto;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.preview-section {
|
||||||
|
h4 {
|
||||||
|
margin: 0 0 10px 0;
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 600;
|
||||||
|
}
|
||||||
|
|
||||||
|
.preview-table {
|
||||||
|
border: 1px solid #d9d9d9;
|
||||||
|
border-radius: 6px;
|
||||||
|
overflow: hidden;
|
||||||
|
max-height: 180px;
|
||||||
|
|
||||||
|
:deep(.ant-table-wrapper) {
|
||||||
|
.ant-table {
|
||||||
|
font-size: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ant-table-thead > tr > th {
|
||||||
|
padding: 8px 8px;
|
||||||
|
font-size: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ant-table-tbody > tr > td {
|
||||||
|
padding: 6px 8px;
|
||||||
|
font-size: 12px;
|
||||||
|
}
|
||||||
|
|
||||||
|
.ant-table-body {
|
||||||
|
max-height: 120px;
|
||||||
|
overflow-y: auto;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 拖拽样式
|
||||||
|
.drag-ghost {
|
||||||
|
opacity: 0.5;
|
||||||
|
background: #f0f0f0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.drop-ghost {
|
||||||
|
background: #e6f7ff;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -1,5 +1,6 @@
|
|||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
import { ref, onMounted, onBeforeUnmount, nextTick } from 'vue';
|
import { message } from 'ant-design-vue/es';
|
||||||
|
import { ref, reactive, onMounted, onBeforeUnmount, nextTick } from 'vue';
|
||||||
import { FitAddon } from '@xterm/addon-fit';
|
import { FitAddon } from '@xterm/addon-fit';
|
||||||
import { Terminal } from '@xterm/xterm';
|
import { Terminal } from '@xterm/xterm';
|
||||||
import '@xterm/xterm/css/xterm.css';
|
import '@xterm/xterm/css/xterm.css';
|
||||||
@@ -31,8 +32,91 @@ const terminalDom = ref<HTMLElement | undefined>(undefined);
|
|||||||
/**终端输入实例对象 */
|
/**终端输入实例对象 */
|
||||||
const terminal = ref<any>(null);
|
const terminal = ref<any>(null);
|
||||||
|
|
||||||
/**终端输入命令 */
|
/**终端输入文字状态 */
|
||||||
const terminalCmd = ref<string>('');
|
const terminalState = reactive<{
|
||||||
|
/**输入值 */
|
||||||
|
text: string;
|
||||||
|
/**历史 */
|
||||||
|
history: {
|
||||||
|
label?: string;
|
||||||
|
value: string;
|
||||||
|
}[];
|
||||||
|
}>({
|
||||||
|
text: '',
|
||||||
|
history: [
|
||||||
|
{
|
||||||
|
value: 'info server',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
value: 'info replication',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
value: 'keys ausf:*',
|
||||||
|
},
|
||||||
|
{
|
||||||
|
value: 'quit',
|
||||||
|
},
|
||||||
|
],
|
||||||
|
});
|
||||||
|
|
||||||
|
/**自动完成根据输入项进行筛选 */
|
||||||
|
function fnAutoCompleteFilter(input: string, option: any) {
|
||||||
|
return option.value.toLowerCase().indexOf(input.toLowerCase()) >= 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**自动完成按键触发 */
|
||||||
|
function fnAutoCompleteKeydown(evt: KeyboardEvent) {
|
||||||
|
if (evt.key === 'Enter') {
|
||||||
|
// 阻止默认的换行行为
|
||||||
|
evt.preventDefault();
|
||||||
|
// 按下 Shift + Enter 键时换行
|
||||||
|
if (evt.shiftKey && evt.target) {
|
||||||
|
// 插入换行符
|
||||||
|
const textarea = evt.target as HTMLInputElement;
|
||||||
|
const start = textarea.selectionStart || 0;
|
||||||
|
const end = textarea.selectionEnd || 0;
|
||||||
|
const text = textarea.value;
|
||||||
|
textarea.value = text.substring(0, start) + '\n' + text.substring(end);
|
||||||
|
terminalState.text = textarea.value;
|
||||||
|
// 更新光标位置
|
||||||
|
textarea.selectionStart = textarea.selectionEnd = start + 1;
|
||||||
|
} else {
|
||||||
|
// ws未连接
|
||||||
|
if (ws.state() !== WebSocket.OPEN) {
|
||||||
|
message.error('disconnected');
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 输入历史
|
||||||
|
const cmdStr = terminalState.text.trim().replace(/\n/g, '\r\n');
|
||||||
|
const hisIndex = terminalState.history.findIndex(
|
||||||
|
item => item.value === cmdStr
|
||||||
|
);
|
||||||
|
if (hisIndex === -1) {
|
||||||
|
terminalState.history.push({
|
||||||
|
value: cmdStr,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// 发送文本
|
||||||
|
terminal.value.scrollToBottom();
|
||||||
|
terminal.value.writeln('\r\n> ' + cmdStr);
|
||||||
|
ws.send({
|
||||||
|
requestId: `redis_${props.hostId}`,
|
||||||
|
type: 'redis',
|
||||||
|
data: `${cmdStr}\r\n`,
|
||||||
|
});
|
||||||
|
terminalState.text = '';
|
||||||
|
|
||||||
|
// 退出登录
|
||||||
|
if (['q', 'quit', 'exit'].includes(cmdStr)) {
|
||||||
|
setTimeout(() => {
|
||||||
|
ws.close();
|
||||||
|
}, 1000);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**终端输入渲染 */
|
/**终端输入渲染 */
|
||||||
function handleRanderXterm(container: HTMLElement | undefined) {
|
function handleRanderXterm(container: HTMLElement | undefined) {
|
||||||
@@ -49,47 +133,13 @@ function handleRanderXterm(container: HTMLElement | undefined) {
|
|||||||
scrollback: 1000,
|
scrollback: 1000,
|
||||||
scrollSensitivity: 15,
|
scrollSensitivity: 15,
|
||||||
tabStopWidth: 4,
|
tabStopWidth: 4,
|
||||||
disableStdin: false, // 禁止输入
|
disableStdin: true, // 禁止输入
|
||||||
});
|
});
|
||||||
// 挂载
|
// 挂载
|
||||||
xterm.open(container);
|
xterm.open(container);
|
||||||
// 自适应尺寸
|
// 自适应尺寸
|
||||||
const fitAddon = new FitAddon();
|
const fitAddon = new FitAddon();
|
||||||
xterm.loadAddon(fitAddon);
|
xterm.loadAddon(fitAddon);
|
||||||
// 终端输入字符按键监听
|
|
||||||
xterm.onKey(({ key, domEvent }) => {
|
|
||||||
// console.log(key, domEvent);
|
|
||||||
// 单键输入
|
|
||||||
switch (domEvent.key) {
|
|
||||||
case 'Enter':
|
|
||||||
const cmdStr = terminalCmd.value.trim();
|
|
||||||
// 发送文本
|
|
||||||
terminal.value.scrollToBottom();
|
|
||||||
terminal.value.writeln('\r\n');
|
|
||||||
ws.send({
|
|
||||||
requestId: `redis_${props.hostId}`,
|
|
||||||
type: 'redis',
|
|
||||||
data: `${cmdStr}\r\n`,
|
|
||||||
});
|
|
||||||
terminalCmd.value = '';
|
|
||||||
|
|
||||||
// 退出登录
|
|
||||||
if ('quit' === cmdStr) {
|
|
||||||
setTimeout(() => {
|
|
||||||
ws.close();
|
|
||||||
}, 1000);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 'Backspace':
|
|
||||||
// 处理退格键,删除最后一个字符
|
|
||||||
xterm.write('\b \b');
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
xterm.write(key);
|
|
||||||
terminalCmd.value += key;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
// 创建 ResizeObserver 实例
|
// 创建 ResizeObserver 实例
|
||||||
var observer = new ResizeObserver(entries => {
|
var observer = new ResizeObserver(entries => {
|
||||||
fitAddon.fit();
|
fitAddon.fit();
|
||||||
@@ -213,7 +263,21 @@ defineExpose({
|
|||||||
|
|
||||||
<template>
|
<template>
|
||||||
<div class="terminal">
|
<div class="terminal">
|
||||||
<div ref="terminalDom" :id="id" class="terminal"></div>
|
<div ref="terminalDom" style="height: calc(100% - 36px)" :id="id"></div>
|
||||||
|
<a-auto-complete
|
||||||
|
v-model:value="terminalState.text"
|
||||||
|
:dropdown-match-select-width="500"
|
||||||
|
style="width: 100%"
|
||||||
|
:options="terminalState.history"
|
||||||
|
:filter-option="fnAutoCompleteFilter"
|
||||||
|
:defaultActiveFirstOption="false"
|
||||||
|
>
|
||||||
|
<a-textarea
|
||||||
|
:auto-size="{ minRows: 1, maxRows: 6 }"
|
||||||
|
placeholder="Execute command. Shift+Enter to line feed, Enter to send"
|
||||||
|
@keypress="fnAutoCompleteKeydown"
|
||||||
|
/>
|
||||||
|
</a-auto-complete>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
|||||||
@@ -80,16 +80,16 @@ function fnAutoCompleteFilter(input: string, option: any) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**自动完成按键触发 */
|
/**自动完成按键触发 */
|
||||||
function fnAutoCompleteKeydown(evt: any) {
|
function fnAutoCompleteKeydown(evt: KeyboardEvent) {
|
||||||
if (evt.key === 'Enter') {
|
if (evt.key === 'Enter') {
|
||||||
// 阻止默认的换行行为
|
// 阻止默认的换行行为
|
||||||
evt.preventDefault();
|
evt.preventDefault();
|
||||||
// 按下 Shift + Enter 键时换行
|
// 按下 Shift + Enter 键时换行
|
||||||
if (evt.shiftKey) {
|
if (evt.shiftKey && evt.target) {
|
||||||
// 插入换行符
|
// 插入换行符
|
||||||
const textarea = evt.target;
|
const textarea = evt.target as HTMLInputElement;
|
||||||
const start = textarea.selectionStart;
|
const start = textarea.selectionStart || 0;
|
||||||
const end = textarea.selectionEnd;
|
const end = textarea.selectionEnd || 0;
|
||||||
const text = textarea.value;
|
const text = textarea.value;
|
||||||
textarea.value = text.substring(0, start) + '\n' + text.substring(end);
|
textarea.value = text.substring(0, start) + '\n' + text.substring(end);
|
||||||
terminalState.text = textarea.value;
|
terminalState.text = textarea.value;
|
||||||
@@ -121,7 +121,7 @@ function fnAutoCompleteKeydown(evt: any) {
|
|||||||
type: 'telnet',
|
type: 'telnet',
|
||||||
data: `${cmdStr}\r\n`,
|
data: `${cmdStr}\r\n`,
|
||||||
});
|
});
|
||||||
terminalState.text = ' ';
|
terminalState.text = '';
|
||||||
|
|
||||||
// 退出登录
|
// 退出登录
|
||||||
if (['q', 'quit', 'exit'].includes(cmdStr)) {
|
if (['q', 'quit', 'exit'].includes(cmdStr)) {
|
||||||
@@ -296,11 +296,12 @@ defineExpose({
|
|||||||
style="width: 100%"
|
style="width: 100%"
|
||||||
:options="terminalState.history"
|
:options="terminalState.history"
|
||||||
:filter-option="fnAutoCompleteFilter"
|
:filter-option="fnAutoCompleteFilter"
|
||||||
@keydown="fnAutoCompleteKeydown"
|
:defaultActiveFirstOption="false"
|
||||||
>
|
>
|
||||||
<a-textarea
|
<a-textarea
|
||||||
:auto-size="{ minRows: 1, maxRows: 6 }"
|
:auto-size="{ minRows: 1, maxRows: 6 }"
|
||||||
placeholder="Execute command. Shift+Enter to line feed, Enter to send"
|
placeholder="Execute command. Shift+Enter to line feed, Enter to send"
|
||||||
|
@keypress="fnAutoCompleteKeydown"
|
||||||
/>
|
/>
|
||||||
</a-auto-complete>
|
</a-auto-complete>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -3,3 +3,6 @@ export const ADMIN_ROLE_KEY = 'system';
|
|||||||
|
|
||||||
/**系统管理员-系统指定权限 */
|
/**系统管理员-系统指定权限 */
|
||||||
export const ADMIN_PERMISSION = '*:*:*';
|
export const ADMIN_PERMISSION = '*:*:*';
|
||||||
|
|
||||||
|
/**次级系统管理员 */
|
||||||
|
export const TENANTADMIN_ROLE_KEY = 'admin';
|
||||||
@@ -1,3 +1,6 @@
|
|||||||
|
/**会话缓存-接口加密 */
|
||||||
|
export const CACHE_SESSION_CRYPTO_API = 'cache:session:cryptoApi';
|
||||||
|
|
||||||
/**会话缓存-网络请求 */
|
/**会话缓存-网络请求 */
|
||||||
export const CACHE_SESSION_FATCH = 'cache:session:fatch';
|
export const CACHE_SESSION_FATCH = 'cache:session:fatch';
|
||||||
|
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ export const NE_TYPE_LIST = [
|
|||||||
'IMS',
|
'IMS',
|
||||||
'AMF',
|
'AMF',
|
||||||
'AUSF',
|
'AUSF',
|
||||||
|
'UDR',
|
||||||
'UDM',
|
'UDM',
|
||||||
'SMF',
|
'SMF',
|
||||||
'PCF',
|
'PCF',
|
||||||
@@ -19,6 +20,8 @@ export const NE_TYPE_LIST = [
|
|||||||
'SMSF',
|
'SMSF',
|
||||||
'CBC',
|
'CBC',
|
||||||
'CHF',
|
'CHF',
|
||||||
|
'HLR',
|
||||||
|
'SGWC',
|
||||||
];
|
];
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -0,0 +1,47 @@
|
|||||||
|
import dayjs from 'dayjs';
|
||||||
|
|
||||||
|
/**日期快捷选择 */
|
||||||
|
export function dayjsRanges() {
|
||||||
|
return [
|
||||||
|
{
|
||||||
|
label: 'Today',
|
||||||
|
value: [dayjs().startOf('day'), dayjs()],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: 'Last 1 hour',
|
||||||
|
value: [
|
||||||
|
dayjs().subtract(1, 'hour').startOf('hour'),
|
||||||
|
dayjs().subtract(1, 'hour').endOf('hour'),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
// {
|
||||||
|
// label: 'Last 3 hour',
|
||||||
|
// value: [dayjs().subtract(3, 'hours'), dayjs()],
|
||||||
|
// },
|
||||||
|
// {
|
||||||
|
// label: 'Last 6 hour',
|
||||||
|
// value: [dayjs().subtract(6, 'hours'), dayjs()],
|
||||||
|
// },
|
||||||
|
{
|
||||||
|
label: 'Last 1 day',
|
||||||
|
value: [
|
||||||
|
dayjs().subtract(1, 'day').startOf('day'),
|
||||||
|
dayjs().subtract(1, 'day').endOf('day'),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: 'Last 7 day',
|
||||||
|
value: [
|
||||||
|
dayjs().subtract(7, 'day').startOf('day'),
|
||||||
|
dayjs().subtract(1, 'day').endOf('day'),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
{
|
||||||
|
label: 'Last 15 day',
|
||||||
|
value: [
|
||||||
|
dayjs().subtract(15, 'day').startOf('day'),
|
||||||
|
dayjs().subtract(1, 'day').endOf('day'),
|
||||||
|
],
|
||||||
|
},
|
||||||
|
];
|
||||||
|
}
|
||||||
@@ -10,13 +10,14 @@ export default {
|
|||||||
desc: 'Core Network Management Platform',
|
desc: 'Core Network Management Platform',
|
||||||
loading: 'Please wait...',
|
loading: 'Please wait...',
|
||||||
inputPlease: 'Please input',
|
inputPlease: 'Please input',
|
||||||
|
searchPlease: 'Search menus...',
|
||||||
|
searchTip: 'Enter keywords to search menus',
|
||||||
selectPlease: 'please select',
|
selectPlease: 'please select',
|
||||||
tipTitle: 'Prompt',
|
tipTitle: 'Prompt',
|
||||||
msgSuccess: 'Success {msg}',
|
msgSuccess: 'Success {msg}',
|
||||||
errorFields: 'Please fill in the required information in {num} correctly!',
|
errorFields: 'Please fill in the required information in {num} correctly!',
|
||||||
tablePaginationTotal: 'Total {total} items',
|
tablePaginationTotal: 'Total {total} items',
|
||||||
noData: "No Data",
|
noData: "No Data",
|
||||||
zebra:'Tabular zebra pattern',
|
|
||||||
ok: 'Ok',
|
ok: 'Ok',
|
||||||
cancel: 'Cancel',
|
cancel: 'Cancel',
|
||||||
close: 'Close',
|
close: 'Close',
|
||||||
@@ -29,6 +30,7 @@ export default {
|
|||||||
editText: 'Edit',
|
editText: 'Edit',
|
||||||
deleteText: 'Delete',
|
deleteText: 'Delete',
|
||||||
downloadText: 'Download',
|
downloadText: 'Download',
|
||||||
|
CloudServerText:'Sync',
|
||||||
import:'Import',
|
import:'Import',
|
||||||
export:'Export',
|
export:'Export',
|
||||||
uploadText: 'Upload',
|
uploadText: 'Upload',
|
||||||
@@ -39,6 +41,11 @@ export default {
|
|||||||
columnSetText: 'Column Setting',
|
columnSetText: 'Column Setting',
|
||||||
columnSetTitle: 'Column Display / Sorting',
|
columnSetTitle: 'Column Display / Sorting',
|
||||||
sizeText: 'Density',
|
sizeText: 'Density',
|
||||||
|
preview:'Preview',
|
||||||
|
exportCustom:'Custom Export',
|
||||||
|
exportColumns:'Column Definition',
|
||||||
|
resetToDefault:'Reset to default columns',
|
||||||
|
exportDefault:'Export',
|
||||||
size: {
|
size: {
|
||||||
default: 'Default',
|
default: 'Default',
|
||||||
middle: 'Medium',
|
middle: 'Medium',
|
||||||
@@ -131,7 +138,7 @@ export default {
|
|||||||
},
|
},
|
||||||
LockScreen: {
|
LockScreen: {
|
||||||
inputPlacePwd:'Lock Screen Password',
|
inputPlacePwd:'Lock Screen Password',
|
||||||
validSucc:'Validation Passed',
|
enter:'Enter',
|
||||||
validError:'Validation Failure',
|
validError:'Validation Failure',
|
||||||
backLogin:'Logout to Relogin',
|
backLogin:'Logout to Relogin',
|
||||||
backReload:'Restarting now, please wait...',
|
backReload:'Restarting now, please wait...',
|
||||||
@@ -143,7 +150,7 @@ export default {
|
|||||||
|
|
||||||
// 静态路由
|
// 静态路由
|
||||||
router: {
|
router: {
|
||||||
index: "Home",
|
index: "Overview",
|
||||||
login: "Sign In",
|
login: "Sign In",
|
||||||
register: 'Registrations',
|
register: 'Registrations',
|
||||||
page403: 'No Access',
|
page403: 'No Access',
|
||||||
@@ -222,12 +229,11 @@ export default {
|
|||||||
capability: 'Capability',
|
capability: 'Capability',
|
||||||
serialNum: 'Serial Number',
|
serialNum: 'Serial Number',
|
||||||
expiryDate: 'Expiry Date',
|
expiryDate: 'Expiry Date',
|
||||||
neStatus: 'NE status is abnormal',
|
neStatus: 'Status Abnormal',
|
||||||
runStatus:'Running Status',
|
runStatus: 'Runing Status',
|
||||||
mark:'Brief Information',
|
mark:'Information',
|
||||||
object:'Object',
|
object:'Object',
|
||||||
versionNum:'Version',
|
versionNum:'Version',
|
||||||
systemStatus:'Status',
|
|
||||||
realNeStatus:'Status',
|
realNeStatus:'Status',
|
||||||
reloadTime:'Refresh Time',
|
reloadTime:'Refresh Time',
|
||||||
Critical:'Critical',
|
Critical:'Critical',
|
||||||
@@ -255,12 +261,16 @@ export default {
|
|||||||
login: {
|
login: {
|
||||||
tabPane1: 'Account password login',
|
tabPane1: 'Account password login',
|
||||||
tabPane2: 'Login with phone number',
|
tabPane2: 'Login with phone number',
|
||||||
registerBtn: 'Register an account',
|
registerBtn: 'Register Account',
|
||||||
loginBtn: 'Sign In',
|
loginBtn: 'Sign In',
|
||||||
loginSuccess: 'Login Successful',
|
loginSuccess: 'Login Successful',
|
||||||
loginMethod: 'Other login methods:',
|
otherMethod: 'Other Methods',
|
||||||
loginMethodWX: 'WeChat Scan Login',
|
backBtn: 'Back',
|
||||||
loginMethodQQ: 'QQ Scan Code Login',
|
backBtnLogin: 'Return Login',
|
||||||
|
authorizedNotfound: 'Authorized Not Found',
|
||||||
|
authorizedFailed: 'Authorized Failed',
|
||||||
|
authorizedSuccess: 'Authorized Successful',
|
||||||
|
redirectHome: 'Redirect to home page in {i} seconds',
|
||||||
},
|
},
|
||||||
register: {
|
register: {
|
||||||
registerBtn: 'Register',
|
registerBtn: 'Register',
|
||||||
@@ -351,178 +361,39 @@ export default {
|
|||||||
description: "No data yet, try refreshing",
|
description: "No data yet, try refreshing",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
configManage: {
|
|
||||||
neManage: {
|
|
||||||
addNe:'Add Network Element',
|
|
||||||
delSure:'Confirm deleting the data item with network element name {msg}',
|
|
||||||
editNe:'Edit Network Element',
|
|
||||||
exportSure:'Confirm exporting the configuration information with the network element name {msg}',
|
|
||||||
exportTip:'Export successful, please go to backup management for download',
|
|
||||||
getInfo:'Failed to get network element information',
|
|
||||||
neType:'NE Type',
|
|
||||||
neTypePlease: 'Select network element type',
|
|
||||||
neId:'NE ID',
|
|
||||||
neName:'NE Name',
|
|
||||||
neTypeTip:'Fill in the type of network element created, such as:SMF',
|
|
||||||
uid:'RM UID',
|
|
||||||
uidTip:'Please enter a unique resource identifier',
|
|
||||||
ip:'IP Address',
|
|
||||||
mac:'NE MAC address',
|
|
||||||
macTip:'Able to locate the physical address (MAC) of the network element',
|
|
||||||
port:'Port',
|
|
||||||
portTip:'Maximum range 0~65535',
|
|
||||||
pvflag:'PV Flag',
|
|
||||||
pnf:'Physical Network Element',
|
|
||||||
vnf:'Virtual Network Element',
|
|
||||||
province:'Region',
|
|
||||||
vendorName:'Vendor Name',
|
|
||||||
dn:'Network Identification',
|
|
||||||
reload: 'Reload',
|
|
||||||
restart: 'Restart',
|
|
||||||
totalSure:'Confirm the network element with {operator} network element name {msg}',
|
|
||||||
stop: 'Stop',
|
|
||||||
start: 'Start',
|
|
||||||
log: 'Logs',
|
|
||||||
export: 'Export',
|
|
||||||
import: 'Import',
|
|
||||||
fileForm:'File Source',
|
|
||||||
selectPlease:'Please select the source of the import file',
|
|
||||||
server:'Server File',
|
|
||||||
local:'Local File',
|
|
||||||
fileSelect:'Please select the current import file',
|
|
||||||
sync:'Synchronize to NE',
|
|
||||||
open:'Open',
|
|
||||||
close:'Close',
|
|
||||||
addFail:'Add failed',
|
|
||||||
operFail:'Operation Failed'
|
|
||||||
},
|
|
||||||
backupManage: {
|
|
||||||
setBackupTask: 'Set automatic backup time',
|
|
||||||
neTypePlease: 'Query network element type',
|
|
||||||
neType: 'NE Type',
|
|
||||||
neID: 'NE ID',
|
|
||||||
fileName: 'File Name',
|
|
||||||
createAt: 'Create at',
|
|
||||||
remark:'Remark',
|
|
||||||
edit:'Edit Backup File',
|
|
||||||
totalSure:'Confirm that {oper} records item number {id}?',
|
|
||||||
},
|
|
||||||
softwareManage: {
|
|
||||||
sendBtn: 'Distribute',
|
|
||||||
runBtn: 'Activate',
|
|
||||||
backBtn: 'Rollback',
|
|
||||||
historyBtn: 'Distribution Record',
|
|
||||||
neTypePlease: 'Select network element type',
|
|
||||||
neType: 'NE Type',
|
|
||||||
fileName: 'File Name',
|
|
||||||
version: 'Version',
|
|
||||||
versionPlease: 'Version number cannot be empty',
|
|
||||||
updateTime: 'Uploaded Time',
|
|
||||||
description: 'Description',
|
|
||||||
deleteTip: 'Are you sure to delete the data item with software [{fileName}]?',
|
|
||||||
downloadTip: 'Are you sure to download the data item with software [{fileName}]?',
|
|
||||||
updateComment: 'Comment',
|
|
||||||
updateCommentPlease: 'Please enter the software description',
|
|
||||||
updateFile: 'Software File',
|
|
||||||
updateFilePlease: 'Please upload the updated software file',
|
|
||||||
verifyFile: 'Verify File',
|
|
||||||
selectFile: 'SELECT FILE',
|
|
||||||
sendTitle: 'Distribute software version',
|
|
||||||
sendContent: 'Are you sure to send the file with the software package [{fileName}] to the corresponding network element?',
|
|
||||||
runTitle: 'Activate software version',
|
|
||||||
runContent: 'Are you sure to activate the software version of [{fileName}] that has been issued to the corresponding network element?',
|
|
||||||
backTitle: 'Fallback software version',
|
|
||||||
backContent: 'Confirm that the software version of [{fileName}] has been issued for the corresponding network element rollback?',
|
|
||||||
neId: 'Corresponding network element',
|
|
||||||
neIdPlease: 'Please select the corresponding network element',
|
|
||||||
versions:'Version',
|
|
||||||
upVersions:'Version before upgrade',
|
|
||||||
backVersions:'Version before rollback',
|
|
||||||
status:'Status',
|
|
||||||
letUpTime:'Activation time',
|
|
||||||
createTime:'Creation time',
|
|
||||||
onlyAble:'Only upload file format {fileText} is supported',
|
|
||||||
nullVersion:'There is no rollback version for the current network element.',
|
|
||||||
},
|
|
||||||
license: {
|
|
||||||
neTypePlease: 'Select network element type',
|
|
||||||
neType: 'NE Type',
|
|
||||||
serialNum: 'Serial Num',
|
|
||||||
createTime: 'Time',
|
|
||||||
comment: 'Description',
|
|
||||||
updateComment: 'License Description',
|
|
||||||
updateCommentPlease: 'Please enter a license description',
|
|
||||||
updateFile: 'License File',
|
|
||||||
updateFilePlease: 'Please upload and update the License file',
|
|
||||||
selectFile: 'SELECT FILE',
|
|
||||||
neId: 'NE ID',
|
|
||||||
neIdPlease: 'Please select the corresponding network element',
|
|
||||||
},
|
|
||||||
configParam:{
|
|
||||||
dataNull:'No configuration item data yet',
|
|
||||||
editSuss:'Modification successful',
|
|
||||||
editFail:'Edit failed',
|
|
||||||
Unable:'Illegal operation of attribute value',
|
|
||||||
delSure:'Confirm to delete the data item with Index [{value}]?',
|
|
||||||
addSuss:'Add successfully',
|
|
||||||
addFail:'Add failed',
|
|
||||||
delArraySure:'Confirm to delete the data item with {arrayChildTitle} Index as [{value}]?',
|
|
||||||
parUnable:'The parameter value is not within the reasonable range',
|
|
||||||
ipv4Tip:'Not a legal IPV4 address',
|
|
||||||
ipv6Tip:'Not a legal IPV6 address',
|
|
||||||
enumTip:'Not a reasonable enumeration value',
|
|
||||||
boolTip:'Not a reasonable Boolean value',
|
|
||||||
default:'The input value is of unknown type',
|
|
||||||
reloadSuss:'Network element reloading completed',
|
|
||||||
reloadFail:'Network element reloading failed',
|
|
||||||
neNUll:'No network element list data yet',
|
|
||||||
reload:'Reload',
|
|
||||||
post:'Submit',
|
|
||||||
editSure:'Are you sure you want to update this attribute value? ',
|
|
||||||
arraryEdit:'Are you sure to submit the record whose updated Index is [{value}]? ',
|
|
||||||
addSure:'Are you sure to submit the new record of Index: [{value}]? '
|
|
||||||
},
|
|
||||||
configParamForm: {
|
|
||||||
treeTitle: "Navigation Configuration",
|
|
||||||
treeSelectTip: "Select configuration item information in the left configuration navigation!",
|
|
||||||
neType: 'NE Type',
|
|
||||||
neTypePleace: "Please select the network element type",
|
|
||||||
noConfigData: "No data on configuration items",
|
|
||||||
updateValue: "[ {num} ] parameter value modified successfully.",
|
|
||||||
updateValueErr: "Attribute value modification failure",
|
|
||||||
updateItem: "Modify Index to {num}.",
|
|
||||||
updateItemErr: "Record modification failure",
|
|
||||||
delItemOk: "Deleting Index as {num} succeeded",
|
|
||||||
addItemOk: "Add Index as {num} Record Succeeded",
|
|
||||||
addItemErr: "Record addition failure",
|
|
||||||
requireUn: "[ {display} ] input value is of unknown type",
|
|
||||||
requireString: "[ {display} ] parameter value is invalid.",
|
|
||||||
requireInt: "[ {display} ] parameter value not in reasonable range {filter}",
|
|
||||||
requireIpv4: "[ {display} ] not a legitimate IPV4 address",
|
|
||||||
requireIpv6: "[ {display} ] not a legitimate IPV6 address.",
|
|
||||||
requireEnum: "[ {display} ] is not a reasonable enumeration value.",
|
|
||||||
requireBool: "[ {display} ] is not a reasonable boolean value.",
|
|
||||||
editOkTip: "Confirm updating the value of this [ {num} ] attribute?",
|
|
||||||
updateItemTip: "Confirm updating the data item with Index [{num}]?",
|
|
||||||
delItemTip: "Confirm deleting the data item with Index [{num}]?",
|
|
||||||
arrayMore: "Expand",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
dashboard: {
|
dashboard: {
|
||||||
overview:{
|
overview:{
|
||||||
title: "Core Network Dashboard",
|
title: "Core Network Dashboard",
|
||||||
fullscreen: "Click on the full-screen display",
|
fullscreen: "Full Screen Display",
|
||||||
toRouter: "Click to jump to the detail page",
|
toRouter: "Click to jump to the detail page",
|
||||||
|
Users:"UDM Subscription Data",
|
||||||
|
VoNR:"IMS Online Users",
|
||||||
|
sessions:"PDU Sessions in SMF",
|
||||||
|
FivegNodeN:"Online gNB in AMF",
|
||||||
|
Fiveusers:"Active users in AMF",
|
||||||
|
FourgNodeN:"Online eNB in MME",
|
||||||
|
Fourusers:"Active users in MME",
|
||||||
|
UPFjump:"Key Performance Indicators",
|
||||||
|
Networkjump:"5GC System Architecture",
|
||||||
|
Alarmjump:"Active Alarms",
|
||||||
|
IMSUsers:"UDM IMS User Data",
|
||||||
|
VoIPUsers:"UDM VoIP User Data",
|
||||||
skim: {
|
skim: {
|
||||||
users: "Users",
|
users: "Total Subscriber Base",
|
||||||
userTitle:'User Information',
|
userTitle:'Subscriber Information',
|
||||||
imsUeNum: "VoNR/VoLTE",
|
imsUeNum: "VoNR/VoLTE",
|
||||||
smfUeNum: "Data Sessions",
|
smfUeNum: "User Sessions",
|
||||||
gnbBase: "Online gNodeB",
|
gnbBase: "Online gNodeB",
|
||||||
|
gnbSumBase: "Total gNodeB",
|
||||||
enbBase: "Online eNodeB",
|
enbBase: "Online eNodeB",
|
||||||
|
enbSumBase: "Total eNodeB",
|
||||||
gnbUeNum:'5G Active Users',
|
gnbUeNum:'5G Active Users',
|
||||||
enbUeNum:'4G Active Users',
|
enbUeNum:'4G Active Users',
|
||||||
baseTitle:'Online Information',
|
baseTitle:'Online Information',
|
||||||
|
nodeBInfo: 'NodeB Information',
|
||||||
|
onlineinfo:'UE Online Information',
|
||||||
|
ims:'VoLTE',
|
||||||
|
voip:'VoIP'
|
||||||
},
|
},
|
||||||
upfFlow:{
|
upfFlow:{
|
||||||
title: "UPF Throughput",
|
title: "UPF Throughput",
|
||||||
@@ -552,6 +423,7 @@ export default {
|
|||||||
},
|
},
|
||||||
userActivity: {
|
userActivity: {
|
||||||
title: "User Activity",
|
title: "User Activity",
|
||||||
|
imsTitle: "IMS Activity",
|
||||||
type: "Type",
|
type: "Type",
|
||||||
duration: "Duration",
|
duration: "Duration",
|
||||||
caller: "Caller",
|
caller: "Caller",
|
||||||
@@ -570,23 +442,32 @@ export default {
|
|||||||
rowInfo: "Info",
|
rowInfo: "Info",
|
||||||
type: "Type",
|
type: "Type",
|
||||||
duration: "Duration",
|
duration: "Duration",
|
||||||
|
mosAverage: "MOS",
|
||||||
|
callConnectionTime: "Call Connection Time",
|
||||||
seizureTime: "Call Start Time",
|
seizureTime: "Call Start Time",
|
||||||
releaseTime: "Hangup Time",
|
releaseTime: "Hangup Time",
|
||||||
caller: "Caller",
|
caller: "Caller",
|
||||||
called: "Called",
|
called: "Called",
|
||||||
result: "Result",
|
result: "Result",
|
||||||
|
resultCode: "Result Code",
|
||||||
|
resultCause: "Result Cause",
|
||||||
resultOk: "Success",
|
resultOk: "Success",
|
||||||
resultFail: "Fail",
|
resultFail: "Fail",
|
||||||
delTip: "Confirm deletion of the data item numbered [{msg}]?",
|
delTip: "Confirm deletion of the data item numbered [{msg}]?",
|
||||||
exportTip: "Do you confirm to export the current query conditions of the CDR data? (Maximum 10,000 items can be exported.)",
|
tenantName: "Tenant Name",
|
||||||
smfChargingID: 'Charging ID',
|
exportTip: "Do you confirm to export the current query conditions of the CDR data?",
|
||||||
|
chargingID: 'Charging ID',
|
||||||
smfSubscriptionIDData: 'Subscription ID Data',
|
smfSubscriptionIDData: 'Subscription ID Data',
|
||||||
smfSubscriptionIDType: 'Subscription ID Type',
|
smfSubscriptionIDType: 'Subscription ID Type',
|
||||||
smfDataVolumeUplink: 'Data Volume Uplink',
|
smfDataVolumeUplink: 'Data Volume Uplink',
|
||||||
smfDataVolumeDownlink: 'Data Volume Downlink',
|
smfDataVolumeDownlink: 'Data Volume Downlink',
|
||||||
smfDataTotalVolume: 'Data Total Volume',
|
smfDataTotalVolume: 'Data Total Volume',
|
||||||
smfDuration: 'Duration',
|
durationTime: 'Duration',
|
||||||
smfInvocationTime: 'Invocation Time',
|
invocationTime: 'Invocation Time',
|
||||||
|
sgwcServedIMSI: 'IMSI',
|
||||||
|
sgwcServedMSISDN: 'MSISDN',
|
||||||
|
sgwcVolumeGPRSUplink: 'GPRS Uplink',
|
||||||
|
sgwcVolumeGPRSDownlink: 'GPRS Downlink',
|
||||||
},
|
},
|
||||||
ue: {
|
ue: {
|
||||||
eventType: "Event Type",
|
eventType: "Event Type",
|
||||||
@@ -598,7 +479,7 @@ export default {
|
|||||||
result: "Result",
|
result: "Result",
|
||||||
resultOk: "Successes",
|
resultOk: "Successes",
|
||||||
delTip: "Confirm deletion of the data item numbered [{msg}]?",
|
delTip: "Confirm deletion of the data item numbered [{msg}]?",
|
||||||
exportTip: "Do you confirm to export the event data of the current query condition? (Maximum 10,000 items can be exported.)",
|
exportTip: "Do you confirm to export the event data of the current query condition?",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
ne: {
|
ne: {
|
||||||
@@ -621,6 +502,8 @@ export default {
|
|||||||
portTip: "Network element port default:33030",
|
portTip: "Network element port default:33030",
|
||||||
serialNum: 'Serial Number',
|
serialNum: 'Serial Number',
|
||||||
expiryDate: 'Expiry Date',
|
expiryDate: 'Expiry Date',
|
||||||
|
ueNumber: 'UE Number',
|
||||||
|
nbNumber: 'Radio Number',
|
||||||
normalcy: 'Normal',
|
normalcy: 'Normal',
|
||||||
exceptions: 'Abnormal',
|
exceptions: 'Abnormal',
|
||||||
restart: 'Restart',
|
restart: 'Restart',
|
||||||
@@ -658,7 +541,7 @@ export default {
|
|||||||
delTip: 'Confirm deletion of network element information data items?',
|
delTip: 'Confirm deletion of network element information data items?',
|
||||||
oam: {
|
oam: {
|
||||||
title: 'OAM Configuration',
|
title: 'OAM Configuration',
|
||||||
sync: 'Sync to NE',
|
restart: 'Restart NE',
|
||||||
oamEnable: 'Service',
|
oamEnable: 'Service',
|
||||||
oamPort: 'Port',
|
oamPort: 'Port',
|
||||||
snmpEnable: 'Service',
|
snmpEnable: 'Service',
|
||||||
@@ -761,14 +644,15 @@ export default {
|
|||||||
upgradeDone: 'Update complete, service being reloaded',
|
upgradeDone: 'Update complete, service being reloaded',
|
||||||
upgradeFail: 'The update fails, please check whether the software file exists and whether the service terminal environment is available!',
|
upgradeFail: 'The update fails, please check whether the software file exists and whether the service terminal environment is available!',
|
||||||
upgradeModal: 'Network Element Version Updates',
|
upgradeModal: 'Network Element Version Updates',
|
||||||
|
noPath: 'Package File Not Found',
|
||||||
},
|
},
|
||||||
neLicense: {
|
neLicense: {
|
||||||
status: "License Status",
|
status: "License Status",
|
||||||
change: "Change License",
|
change: "Change License",
|
||||||
reload: "Refresh Info",
|
reload: "Refresh Info",
|
||||||
reloadTip: "Confirmed to refresh license information?",
|
reloadTip: "Confirmed to refresh license information?",
|
||||||
reloadBatch: "Batch Refresh",
|
reloadBatch: "Refresh License Status",
|
||||||
reloadBatchTip: "Do you do an information refresh on checked records?",
|
reloadBatchTip: "Do you perform a license status information refresh for the current list of NE?",
|
||||||
updateTtile: "Update License",
|
updateTtile: "Update License",
|
||||||
downCodeTop: "Confirmed to save the license activation code to a file?",
|
downCodeTop: "Confirmed to save the license activation code to a file?",
|
||||||
activationRequestCode: "License Activation Code",
|
activationRequestCode: "License Activation Code",
|
||||||
@@ -784,7 +668,9 @@ export default {
|
|||||||
treeSelectTip: "Select configuration item information in the left configuration navigation!",
|
treeSelectTip: "Select configuration item information in the left configuration navigation!",
|
||||||
neType: 'NE Type',
|
neType: 'NE Type',
|
||||||
neTypePleace: "Please select the network element type",
|
neTypePleace: "Please select the network element type",
|
||||||
|
neIdSyncPleace: "Please select the synchronized network element",
|
||||||
noConfigData: "No data on configuration items",
|
noConfigData: "No data on configuration items",
|
||||||
|
noConfigdDisabled: "The configuration item is not normal",
|
||||||
updateValue: "[ {num} ] parameter value modified successfully.",
|
updateValue: "[ {num} ] parameter value modified successfully.",
|
||||||
updateValueErr: "Attribute value modification failure",
|
updateValueErr: "Attribute value modification failure",
|
||||||
updateItem: "Modify Index to {num}.",
|
updateItem: "Modify Index to {num}.",
|
||||||
@@ -808,6 +694,19 @@ export default {
|
|||||||
name: "Name",
|
name: "Name",
|
||||||
downTip: 'Confirmed to download the backup file [{txt}]?',
|
downTip: 'Confirmed to download the backup file [{txt}]?',
|
||||||
title: "Modify Backup {txt}",
|
title: "Modify Backup {txt}",
|
||||||
|
backupModal: {
|
||||||
|
pushFileOper: "Send Current File To Remote Backup",
|
||||||
|
title: "Setting Remote Backup Service",
|
||||||
|
enable: "Enable",
|
||||||
|
toIp: "Service IP",
|
||||||
|
toIpPleace: "Please input the remote backup server IP address",
|
||||||
|
toPort: "Service Port",
|
||||||
|
username: "UserName",
|
||||||
|
usernamePleace: 'Please enter the service login username',
|
||||||
|
password: "Password",
|
||||||
|
dir: "Save Dir",
|
||||||
|
dirPleace: 'Please enter the service address target file directory',
|
||||||
|
}
|
||||||
},
|
},
|
||||||
neQuickSetup: {
|
neQuickSetup: {
|
||||||
reloadPara5G: 'Reload',
|
reloadPara5G: 'Reload',
|
||||||
@@ -845,7 +744,7 @@ export default {
|
|||||||
installSourceUpload: 'New Upload',
|
installSourceUpload: 'New Upload',
|
||||||
installSelect: 'Select Record',
|
installSelect: 'Select Record',
|
||||||
installUpload: 'Upload File',
|
installUpload: 'Upload File',
|
||||||
installText: 'Installed',
|
installText: 'Install',
|
||||||
licenseTitle: "Licenses",
|
licenseTitle: "Licenses",
|
||||||
licenseDesc: "Network element service authorization certification",
|
licenseDesc: "Network element service authorization certification",
|
||||||
licenseResultTitle: "Whether to authorize activation immediately",
|
licenseResultTitle: "Whether to authorize activation immediately",
|
||||||
@@ -858,9 +757,61 @@ export default {
|
|||||||
licenseTip2: '2. Clicking [Finish] will end the installation process.',
|
licenseTip2: '2. Clicking [Finish] will end the installation process.',
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
neData: {
|
||||||
|
common: {
|
||||||
|
startIMSI: 'Starting IMSI',
|
||||||
|
imsi: 'IMSI',
|
||||||
|
imsiTip: 'IMSI=MCC+MNC+MSIN',
|
||||||
|
imsiTip1: 'MCC=Mobile Country Code, consisting of three digits.',
|
||||||
|
imsiTip2: 'MNC = Mobile Network Number, consisting of two digits',
|
||||||
|
imsiTip3: 'MSIN = Mobile Subscriber Identification Number, consisting of 10 equal digits.',
|
||||||
|
imsiPlease: "Please enter IMSI correctly",
|
||||||
|
msisdn: 'Mobile Customer Identification Number',
|
||||||
|
msisdnPlease: "Please enter the Mobile Customer Identification Number correctly",
|
||||||
|
loadDataConfirm: 'Confirmed to reload data?',
|
||||||
|
loadData: 'Load Data',
|
||||||
|
loadDataTip: 'Successfully fetched loaded data: {num} items, the system is internally updating the data, it will take about {timer} seconds, please wait!!!!!.',
|
||||||
|
batchOper: 'Batch Operation',
|
||||||
|
batchAddText: 'Batch Addition',
|
||||||
|
batchDelText: 'Batch Deletion',
|
||||||
|
batchUpdateText: 'Batch Update',
|
||||||
|
batchNum: 'Number of releases',
|
||||||
|
checkDel:'Check Delete',
|
||||||
|
importTemplate: 'Download Template',
|
||||||
|
},
|
||||||
|
baseStation: {
|
||||||
|
list: "List",
|
||||||
|
topology: "Topology",
|
||||||
|
nbName: "RAN Node Name",
|
||||||
|
nbId: "RAN Node ID",
|
||||||
|
ueNum: "UE Number",
|
||||||
|
topologyTitle: "Radio State Graph",
|
||||||
|
name: "Name",
|
||||||
|
namePlease: "text content length 0~64",
|
||||||
|
position: "Position",
|
||||||
|
positionPlease: "location description. Prohibition of spaces, length of text content 0-64",
|
||||||
|
address: "IP Address",
|
||||||
|
addressPlease: "text content length 0~64",
|
||||||
|
state: "State",
|
||||||
|
online: "Online",
|
||||||
|
offline: "Offline",
|
||||||
|
time: "Change Time",
|
||||||
|
addRadio: "Add Radio Info",
|
||||||
|
editRadio: "Edit Radio Info",
|
||||||
|
history: "Status History",
|
||||||
|
exportTip: "Confirm exporting xlsx table files based on search criteria?",
|
||||||
|
importDataEmpty: "Imported data is empty",
|
||||||
|
},
|
||||||
|
backupData: {
|
||||||
|
auth: "UDM Authentication",
|
||||||
|
sub: "UDM Subscribers",
|
||||||
|
voip: "VoIP Authentication",
|
||||||
|
volte: "IMS Subscribers",
|
||||||
|
}
|
||||||
|
},
|
||||||
neUser: {
|
neUser: {
|
||||||
auth: {
|
auth: {
|
||||||
authInfo:' Authentication Info',
|
authInfo:' Authentication of Info',
|
||||||
neTypePlease: 'Query network element Object',
|
neTypePlease: 'Query network element Object',
|
||||||
neType: 'UDM Object',
|
neType: 'UDM Object',
|
||||||
export: 'Export',
|
export: 'Export',
|
||||||
@@ -868,13 +819,14 @@ export default {
|
|||||||
checkExport : 'Check Export',
|
checkExport : 'Check Export',
|
||||||
checkExportConfirm: 'Confirm exporting the checked authenticated user data?',
|
checkExportConfirm: 'Confirm exporting the checked authenticated user data?',
|
||||||
import: 'Import',
|
import: 'Import',
|
||||||
|
importFail: 'Failure Record',
|
||||||
loadDataConfirm: 'Are you sure you want to reload the data?',
|
loadDataConfirm: 'Are you sure you want to reload the data?',
|
||||||
loadData: 'Load Data',
|
loadData: 'Load Data',
|
||||||
loadDataTip: 'Successfully fetched loaded data: {num} items, the system is internally updating the data, it will take about {timer} seconds, please wait!!!!!.',
|
loadDataTip: 'Successfully fetched loaded data: {num} items, the system is internally updating the data, it will take about {timer} seconds, please wait!!!!!.',
|
||||||
startIMSI: 'Start IMSI',
|
startIMSI: 'Start IMSI',
|
||||||
batchAddText: 'Batch Add',
|
batchAddText: 'Batch Add',
|
||||||
batchDelText: 'Batch Delete',
|
batchDelText: 'Batch Delete',
|
||||||
numAdd: 'Number of releases',
|
numAdd: 'Number of authentication profiles',
|
||||||
numDel: 'Number of deleted',
|
numDel: 'Number of deleted',
|
||||||
checkDel: 'Check Delete',
|
checkDel: 'Check Delete',
|
||||||
imsiTip: 'IMSI=MCC+MNC+MSIN',
|
imsiTip: 'IMSI=MCC+MNC+MSIN',
|
||||||
@@ -887,19 +839,22 @@ export default {
|
|||||||
opcTip: 'The authentication key, OPC, is calculated from Ki and OP, OP is the root key of the operator, ki is the authentication key, and the maximum length is 32.',
|
opcTip: 'The authentication key, OPC, is calculated from Ki and OP, OP is the root key of the operator, ki is the authentication key, and the maximum length is 32.',
|
||||||
delSure:'Are you sure you want to delete the user with IMSI number: {imsi} ?',
|
delSure:'Are you sure you want to delete the user with IMSI number: {imsi} ?',
|
||||||
imsiConfirm:'The length of the IMSI must be 15',
|
imsiConfirm:'The length of the IMSI must be 15',
|
||||||
|
startUserName:'Start username',
|
||||||
},
|
},
|
||||||
sub: {
|
sub: {
|
||||||
subInfo:' Subscription Info',
|
subInfo:' Subscription Info',
|
||||||
neType: 'UDM Object',
|
neType: 'UDM Object',
|
||||||
|
imsType:'IMS Object',
|
||||||
export: 'Export',
|
export: 'Export',
|
||||||
exportConfirm: 'Are you sure to export all signed user data?',
|
exportConfirm: 'Are you sure to export all signed user data?',
|
||||||
checkExport : 'Check Export',
|
checkExport : 'Check Export',
|
||||||
checkExportConfirm: 'Are you sure to export the data of the checked subscribers?',
|
checkExportConfirm: 'Are you sure to export the data of the checked subscribers?',
|
||||||
import: 'Import',
|
import: 'Import',
|
||||||
|
importFail: 'Failure Record',
|
||||||
loadDataConfirm: 'Are you sure you want to reload the data?',
|
loadDataConfirm: 'Are you sure you want to reload the data?',
|
||||||
loadData: 'Load Data',
|
loadData: 'Load Data',
|
||||||
loadDataTip: 'Successfully fetched loaded data: {num} items, the system is internally updating the data, it will take about {timer} seconds, please wait!!!!!.',
|
loadDataTip: 'Successfully fetched loaded data: {num} items, the system is internally updating the data, it will take about {timer} seconds, please wait!!!!!.',
|
||||||
numAdd: 'Number of releases',
|
numAdd: 'Number of subscriber profiles',
|
||||||
numDel: 'Number of deleted',
|
numDel: 'Number of deleted',
|
||||||
checkDel: 'Check Delete',
|
checkDel: 'Check Delete',
|
||||||
batchAddText: 'Batch Add',
|
batchAddText: 'Batch Add',
|
||||||
@@ -919,6 +874,10 @@ export default {
|
|||||||
rfspTip:'RFSP index, in NG-RAN, the index of a specific RRM configuration, parameter between 0 and 127',
|
rfspTip:'RFSP index, in NG-RAN, the index of a specific RRM configuration, parameter between 0 and 127',
|
||||||
ueTypeTip: 'Operator-defined subscriber UE Usage Type, integer, parameter between 0 and 127',
|
ueTypeTip: 'Operator-defined subscriber UE Usage Type, integer, parameter between 0 and 127',
|
||||||
cnFlag: 'Whether to enable 5G Core Network service',
|
cnFlag: 'Whether to enable 5G Core Network service',
|
||||||
|
cnFlag0: 'No Access Allowed',
|
||||||
|
cnFlag1: 'Access Only 5G',
|
||||||
|
cnFlag2: 'Access Only 4G',
|
||||||
|
cnFlag3: 'Access 4G/5G',
|
||||||
epsFlagTip: 'Whether to enable 4G EPS service',
|
epsFlagTip: 'Whether to enable 4G EPS service',
|
||||||
contextIdTip: 'To sign up for an APN Context ID, you must select it from the APN Context list.',
|
contextIdTip: 'To sign up for an APN Context ID, you must select it from the APN Context list.',
|
||||||
apnContextTip: 'The list of APNs available to the phone, up to six, is defined in the HSS.',
|
apnContextTip: 'The list of APNs available to the phone, up to six, is defined in the HSS.',
|
||||||
@@ -928,6 +887,12 @@ export default {
|
|||||||
ardTip:'Access-Restriction-Data (Access-Restriction-Data), can be used to distinguish between 2G/3G/LTE users, to facilitate the coexistence of 2G/3G/LTE network for different types of users to distinguish between the service',
|
ardTip:'Access-Restriction-Data (Access-Restriction-Data), can be used to distinguish between 2G/3G/LTE users, to facilitate the coexistence of 2G/3G/LTE network for different types of users to distinguish between the service',
|
||||||
smDataTip:'The IP in sm_data=1-000001&internet-1.2.3.4&ims-1.2.3.5: 1.2.3.4 is the static IP assigned to the APN of 5G user internet, and 1.2.3.5 is the static IP assigned to the APN of 5G user ims. If it is dynamic allocation, just remove the IP and the previous connector. Need to support multiple dnn uses & connections',
|
smDataTip:'The IP in sm_data=1-000001&internet-1.2.3.4&ims-1.2.3.5: 1.2.3.4 is the static IP assigned to the APN of 5G user internet, and 1.2.3.5 is the static IP assigned to the APN of 5G user ims. If it is dynamic allocation, just remove the IP and the previous connector. Need to support multiple dnn uses & connections',
|
||||||
smDataArrTip:'SST,DNN/APN is required',
|
smDataArrTip:'SST,DNN/APN is required',
|
||||||
|
tenantName:'Tenant Name',
|
||||||
|
imsiMode:'IMSI Matching Mode',
|
||||||
|
fuzzyMatch:'Fuzzy Match',
|
||||||
|
prefixMatch:'Prefix Match',
|
||||||
|
fullMatch:'Full Match',
|
||||||
|
suffixMatch:'Suffix Match',
|
||||||
},
|
},
|
||||||
pcf: {
|
pcf: {
|
||||||
neType: 'PCF Object',
|
neType: 'PCF Object',
|
||||||
@@ -961,7 +926,9 @@ export default {
|
|||||||
rfsfTip:'RAT Frequency Selection Priority',
|
rfsfTip:'RAT Frequency Selection Priority',
|
||||||
},
|
},
|
||||||
base5G: {
|
base5G: {
|
||||||
neType: 'NE Object',
|
neType: 'Radio Type',
|
||||||
|
gnb:'5G Radios',
|
||||||
|
enb:'4G Radios',
|
||||||
},
|
},
|
||||||
n3iwf: {
|
n3iwf: {
|
||||||
neType: 'N3IWF Object',
|
neType: 'N3IWF Object',
|
||||||
@@ -1073,8 +1040,13 @@ export default {
|
|||||||
expression:'Expression',
|
expression:'Expression',
|
||||||
description:' Description',
|
description:' Description',
|
||||||
kpiSet:' Statistical Settings',
|
kpiSet:' Statistical Settings',
|
||||||
sixHoursAgo:'Six hours ago',
|
ago1Hour:'Last 1 hour',
|
||||||
threeHoursAgo:'Three hours ago.',
|
ago3Hour:'Last 3 hour',
|
||||||
|
ago6Hour:'Last 6 hour',
|
||||||
|
toDay:'Today',
|
||||||
|
ago1Day:'Last 1 day',
|
||||||
|
ago7Day:'Last 7 day',
|
||||||
|
ago15Day:'Last 15 day',
|
||||||
delCustomTip:'Confirm deletion of data item with record Custom Indicator {num}?',
|
delCustomTip:'Confirm deletion of data item with record Custom Indicator {num}?',
|
||||||
delCustom:' Successfully delete record number {num} custom indicator',
|
delCustom:' Successfully delete record number {num} custom indicator',
|
||||||
addCustom:' Add custom indicator',
|
addCustom:' Add custom indicator',
|
||||||
@@ -1090,6 +1062,12 @@ export default {
|
|||||||
expressionModal:'Expression Modal',
|
expressionModal:'Expression Modal',
|
||||||
expressionErrorTip:'Please check the expression, the wrong indicator is {kpiId}',
|
expressionErrorTip:'Please check the expression, the wrong indicator is {kpiId}',
|
||||||
expressionNoIdTip:'Please check the expression, no valid indicator is found',
|
expressionNoIdTip:'Please check the expression, no valid indicator is found',
|
||||||
|
unitSelect:'To better display the image, the same unit needs to be selected. The current unit is:',
|
||||||
|
avg:'(average)',
|
||||||
|
total:'(total)',
|
||||||
|
ago1:'Past 24 hrs value',
|
||||||
|
ago7:'Past 7 days value',
|
||||||
|
ago30:'Past 30 days value',
|
||||||
},
|
},
|
||||||
kpiKeyTarget:{
|
kpiKeyTarget:{
|
||||||
"time":"Time",
|
"time":"Time",
|
||||||
@@ -1108,35 +1086,38 @@ export default {
|
|||||||
},
|
},
|
||||||
kpiOverView:{
|
kpiOverView:{
|
||||||
"kpiName":"NE Metrics Name",
|
"kpiName":"NE Metrics Name",
|
||||||
"maxValue":"Max Value",
|
"maxValue":"Max",
|
||||||
"minValue":"Min Value",
|
"maxValueTip":"The max value of metric data within the user's filtered time range.",
|
||||||
|
"minValue":"Min",
|
||||||
|
"minValueTip":"The min value of metric data within the user's filtered time range.",
|
||||||
|
"avgValue":"Avg",
|
||||||
|
"avgValueTip":"The average value of metric data within the user's filtered time range.",
|
||||||
|
"totalValue":"Sum",
|
||||||
|
"totalValueTip":"The sum value of metric data within the user's filtered time range.",
|
||||||
"kpiChartTitle":"Overview of NE metrics",
|
"kpiChartTitle":"Overview of NE metrics",
|
||||||
"changeLine":"Change to Line Charts",
|
"changeLine":"Change to Line Charts",
|
||||||
"changeBar":"Change to Bar Charts",
|
"changeBar":"Change to Bar Charts",
|
||||||
"chooseShowMetrics":"Select the metric you want to display",
|
"chooseShowMetrics":"Select the metric you want to display",
|
||||||
"chooseMetrics":"Select an indicator",
|
"chooseMetrics":"Select an indicator",
|
||||||
|
"tips":"The percentages and rates are averages,the counts are statistical values.",
|
||||||
|
},
|
||||||
|
voiceOverView:{
|
||||||
|
"voiceTitle":"Voice Calls Dashboard",
|
||||||
|
"tips":"Voice Call Statistics Per Minute",
|
||||||
|
"ne":"NE",
|
||||||
|
"now":"Now",
|
||||||
|
"last":"Past",
|
||||||
|
"calls":"Calls",
|
||||||
|
"activeCall":"Active Calls",
|
||||||
|
"callMOMT":"MO/MT Call Success Rate",
|
||||||
|
"failedcall":"Failed Calls",
|
||||||
|
"registration":"Registrations",
|
||||||
|
"activeregistration":"Active Registrations",
|
||||||
|
"registrationsuccess":"Registration Success Rate",
|
||||||
|
"failedregistration":"Failed Registrations",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
traceManage: {
|
traceManage: {
|
||||||
analysis: {
|
|
||||||
imsi: 'IMSI',
|
|
||||||
imsiPlease: 'Please enter IMSI',
|
|
||||||
msisdn: 'MSISDN',
|
|
||||||
msisdnPlease: 'Please enter MSISDN',
|
|
||||||
trackTaskId: 'Task ID',
|
|
||||||
srcIp: 'Source IP Address',
|
|
||||||
dstIp: 'Destination IP Address',
|
|
||||||
signalType: 'Signaling Type',
|
|
||||||
msgDirect: 'Message Direction',
|
|
||||||
msgType: 'Message Type',
|
|
||||||
rowTime: 'Record Time',
|
|
||||||
signalData: 'Signaling Data',
|
|
||||||
signalDetail: 'Signaling Details',
|
|
||||||
noData: 'No information content',
|
|
||||||
taskTitle: 'Task {num}',
|
|
||||||
taskDownText: 'Download HTML',
|
|
||||||
taskDownTip: 'Confirm downloading the signaling details HTML file?',
|
|
||||||
},
|
|
||||||
pcap: {
|
pcap: {
|
||||||
capArgPlease: 'Please enter tcpdump -i any support parameter',
|
capArgPlease: 'Please enter tcpdump -i any support parameter',
|
||||||
cmd: 'Command',
|
cmd: 'Command',
|
||||||
@@ -1171,6 +1152,7 @@ export default {
|
|||||||
},
|
},
|
||||||
task: {
|
task: {
|
||||||
traceId: 'Tracing No',
|
traceId: 'Tracing No',
|
||||||
|
title: 'Tracing Title',
|
||||||
trackType: 'Tracing Type',
|
trackType: 'Tracing Type',
|
||||||
trackTypePlease: 'Please select a tracing type',
|
trackTypePlease: 'Please select a tracing type',
|
||||||
creater: 'Created by',
|
creater: 'Created by',
|
||||||
@@ -1187,30 +1169,35 @@ export default {
|
|||||||
imsiTip: 'Mobile communication IMSI number',
|
imsiTip: 'Mobile communication IMSI number',
|
||||||
srcIp: 'Source IP Address',
|
srcIp: 'Source IP Address',
|
||||||
srcIpPlease: 'Please enter the IP address',
|
srcIpPlease: 'Please enter the IP address',
|
||||||
srcIpTip: 'Current sender IPv4 address',
|
srcIpTip: 'sending IPv4 address',
|
||||||
dstIp: 'Destination IP Address',
|
dstIp: 'Destination IP Address',
|
||||||
dstIpPlease: 'Please enter the IP address',
|
dstIpPlease: 'Please enter the IP address',
|
||||||
dstIpTip: 'IPv4 address of the receiving end of the other party',
|
dstIpTip: 'receiving end IPv4 address',
|
||||||
interfaces: 'Signaling Interface',
|
interfaces: 'Signaling Interface',
|
||||||
interfacesPlease: 'Please enter the signaling interface',
|
interfacesPlease: 'Please enter the signaling interface',
|
||||||
signalPort: 'Signal Port',
|
rangePicker: 'Task Time',
|
||||||
signalPortPlease: 'Please enter the signaling port',
|
|
||||||
signalPortTip: 'Port of the side corresponding to the destination IP address or source IP address',
|
|
||||||
rangePicker: 'Start/End Time',
|
|
||||||
rangePickerPlease: 'Please select the start and end time of the task',
|
rangePickerPlease: 'Please select the start and end time of the task',
|
||||||
remark: 'Remark',
|
remark: 'Remark',
|
||||||
remarkPlease: 'Task description can be entered',
|
remarkPlease: 'Task description can be entered',
|
||||||
addTask: 'Add Task',
|
addTask: 'Add Task',
|
||||||
editTask: 'Modify Task',
|
|
||||||
viewTask: 'View Task',
|
viewTask: 'View Task',
|
||||||
errorTaskInfo: 'Failed to obtain task information',
|
errorTaskInfo: 'Failed to obtain task information',
|
||||||
delTaskTip: 'Are you sure to delete the data item with record ID {id} ?',
|
delTaskTip: 'Are you sure to delete the data item with record ID {id} ?',
|
||||||
stopTask: 'Successful cessation of tasks {id}',
|
stopTask: 'Successful cessation of tasks {id}',
|
||||||
stopTaskTip: 'Confirm stopping the task with record ID {id} ?',
|
stopTaskTip: 'Confirm stopping the task with record ID {id} ?',
|
||||||
pcapView: "Tracking Data Analysis",
|
pcapView: "Track Data Analysis",
|
||||||
traceFile: "Tracking File",
|
traceFile: "Track File",
|
||||||
errMsg: "Error Message",
|
errMsg: "Error Message",
|
||||||
imsiORmsisdn: "imsi or msisdn is null, cannot start task",
|
imsiORmsisdn: "imsi or msisdn is null, cannot start task",
|
||||||
|
dataView: "Track Data",
|
||||||
|
protocolOrInterface: "Protocol/Interface",
|
||||||
|
msgNe: 'Network Element',
|
||||||
|
msgEvent: 'Event',
|
||||||
|
msgType: 'Type',
|
||||||
|
msgDirect: 'Direction',
|
||||||
|
msgLen: 'Length',
|
||||||
|
rowTime: 'Time',
|
||||||
|
taskInfo: 'Task information',
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
faultManage: {
|
faultManage: {
|
||||||
@@ -1230,7 +1217,7 @@ export default {
|
|||||||
clear: 'Clear',
|
clear: 'Clear',
|
||||||
mySelf: 'Personalization',
|
mySelf: 'Personalization',
|
||||||
exportAll: 'Export All',
|
exportAll: 'Export All',
|
||||||
disPlayFilfter: 'Display Filters',
|
disPlayFilfter: 'Filter out Alerts',
|
||||||
alarmId:'ID',
|
alarmId:'ID',
|
||||||
alarmTitle:'Title',
|
alarmTitle:'Title',
|
||||||
clearUser:'Clear User',
|
clearUser:'Clear User',
|
||||||
@@ -1320,22 +1307,30 @@ export default {
|
|||||||
size: "Size",
|
size: "Size",
|
||||||
modifiedTime: "Modified Time",
|
modifiedTime: "Modified Time",
|
||||||
fileName: "File Name",
|
fileName: "File Name",
|
||||||
|
downTipZip: "Confirm downloading the directory [{fileName}] as a ZIP file?",
|
||||||
downTip: "Confirm the download file name is [{fileName}] File?",
|
downTip: "Confirm the download file name is [{fileName}] File?",
|
||||||
downTipErr: "Failed to get file",
|
downTipErr: "Failed to get file",
|
||||||
dirCd: "Enter Dir",
|
dirCd: "Enter Dir",
|
||||||
viewAs: 'View Action',
|
viewAs: 'View Action',
|
||||||
reload: "Reload",
|
reload: "Reload",
|
||||||
follow: 'Monitoring Content',
|
follow: 'Enable Instant Update',
|
||||||
tailChar: 'End Characters',
|
tailChar: 'End Characters',
|
||||||
tailLines: 'End Lines',
|
tailLines: 'End Lines',
|
||||||
},
|
},
|
||||||
exportFile:{
|
exportFile:{
|
||||||
fileName:'File Source',
|
fileSource:'File Source',
|
||||||
|
fileSourcePlease:'Please select the source of the document',
|
||||||
downTip: "Confirm the download file name is [{fileName}] File?",
|
downTip: "Confirm the download file name is [{fileName}] File?",
|
||||||
downTipErr: "Failed to get file",
|
downTipErr: "Failed to get file",
|
||||||
deleteTip: "Confirm the delete file name is [{fileName}] File?",
|
deleteTip: "Confirm the delete file name is [{fileName}] File?",
|
||||||
deleteTipErr: "Failed to delete file",
|
deleteTipErr: "Failed to delete file",
|
||||||
selectTip:"Please select File Name",
|
sysloginLog:'System Login Log',
|
||||||
|
sysOperateLog:'System Operation Log',
|
||||||
|
neLog:'NE Log',
|
||||||
|
cdrIMS:'CDR Voice',
|
||||||
|
cdrSMF:'CDR Data',
|
||||||
|
cdrSMSC:'CDR SMS',
|
||||||
|
cdrSGWC:'CDR Roaming Data',
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
monitor: {
|
monitor: {
|
||||||
@@ -1709,6 +1704,8 @@ export default {
|
|||||||
userName: 'Nick Name',
|
userName: 'Nick Name',
|
||||||
permission: 'Role',
|
permission: 'Role',
|
||||||
className: 'Department',
|
className: 'Department',
|
||||||
|
userType: 'User Type',
|
||||||
|
tenntName:'Tenant Name',
|
||||||
loginIp: 'Login Address',
|
loginIp: 'Login Address',
|
||||||
loginTime: 'Login Time',
|
loginTime: 'Login Time',
|
||||||
status: 'Status',
|
status: 'Status',
|
||||||
@@ -1734,6 +1731,7 @@ export default {
|
|||||||
sex:'User Gender',
|
sex:'User Gender',
|
||||||
email:'E-mail',
|
email:'E-mail',
|
||||||
fromClass:'Department',
|
fromClass:'Department',
|
||||||
|
fromTenant:'Tenant',
|
||||||
userWork:'User position',
|
userWork:'User position',
|
||||||
userWorkPlease: 'Please select user post',
|
userWorkPlease: 'Please select user post',
|
||||||
userTip:'User Description',
|
userTip:'User Description',
|
||||||
@@ -1747,6 +1745,7 @@ export default {
|
|||||||
lock:'Lock',
|
lock:'Lock',
|
||||||
inactive:'Inactive',
|
inactive:'Inactive',
|
||||||
active:'Active',
|
active:'Active',
|
||||||
|
permissionTip:'If want to select a tenant role, make sure there is at least one tenant in the tenant management.',
|
||||||
},
|
},
|
||||||
config: {
|
config: {
|
||||||
configName: "Config Name",
|
configName: "Config Name",
|
||||||
@@ -1771,6 +1770,55 @@ export default {
|
|||||||
refreshCacheTip: "Are you sure you want to refresh the parameter configuration cache?",
|
refreshCacheTip: "Are you sure you want to refresh the parameter configuration cache?",
|
||||||
refreshCacheOk: "Refresh Cache Successful",
|
refreshCacheOk: "Refresh Cache Successful",
|
||||||
},
|
},
|
||||||
|
loginSource: {
|
||||||
|
uid: "UID",
|
||||||
|
name: "Name",
|
||||||
|
namePlease: 'Please enter the authentication source name correctly',
|
||||||
|
icon: "Icon",
|
||||||
|
iconPlease: 'You can enter the image link or upload the image path address',
|
||||||
|
type: "Type",
|
||||||
|
activeFlag: "Status",
|
||||||
|
remark: "Remark",
|
||||||
|
createTime: "Create Time",
|
||||||
|
updateTime: "Update Time",
|
||||||
|
ldapUrl: "Server Address",
|
||||||
|
ldapUrlPlease: 'Please enter the LDAP server address correctly',
|
||||||
|
ldapBaseDN: "Base DN",
|
||||||
|
baseDnPlease: 'Please enter the LDAP base DN correctly',
|
||||||
|
ldapUserFilter: "User Filter",
|
||||||
|
userFilterPlease: 'Please enter the LDAP user filter correctly',
|
||||||
|
ldapBindDN: "Bind DN",
|
||||||
|
ldapBindPassword: "Bind Password",
|
||||||
|
smtpHost: 'Server Address',
|
||||||
|
smtpHostPlease: 'Please enter the SMTP server address correctly',
|
||||||
|
smtpPort: 'Port Number',
|
||||||
|
smtpPortPlease: 'Please enter the SMTP port number correctly',
|
||||||
|
oauth2ClientID: 'Client ID',
|
||||||
|
oauth2ClientIDPlease: 'Please enter the OAuth2 client ID correctly',
|
||||||
|
oauth2ClientSecret: 'Client Secret',
|
||||||
|
oauth2ClientSecretPlease: 'Please enter the OAuth2 client secret correctly',
|
||||||
|
oauth2AuthURL: 'Authorization URL',
|
||||||
|
oauth2AuthURLPlease: 'Please enter the OAuth2 authorization URL correctly',
|
||||||
|
oauth2TokenURL: 'Token URL',
|
||||||
|
oauth2TokenURLPlease: 'Please enter the OAuth2 token URL correctly',
|
||||||
|
oauth2UserURL: 'User Info URL',
|
||||||
|
oauth2UserURLPlease: 'Please enter the OAuth2 user info URL correctly',
|
||||||
|
oauth2AccountField: 'Account Field',
|
||||||
|
oauth2AccountFieldPlease: 'Please enter the OAuth2 account field correctly',
|
||||||
|
oauth2Scopes: 'Scopes',
|
||||||
|
oauth2ScopesPlease: 'Please enter the OAuth2 scopes correctly',
|
||||||
|
oauth2RedirectURL: 'Redirect URL',
|
||||||
|
oauth2RedirectURLPlease: 'Please enter the OAuth2 redirect URL correctly',
|
||||||
|
oauth2RedirectURLTip: 'Please jump to the specified path (omchost/#/login/oauth2), redirect with code and state address parameters',
|
||||||
|
uploadFileTip: 'Confirm to upload the authentication source icon?',
|
||||||
|
uploadFileOk: 'Authentication source icon upload successful',
|
||||||
|
uploadFileErr: 'Authentication source icon upload failed',
|
||||||
|
viewInfoErr: "Failed to get authentication source information",
|
||||||
|
addInfo: "Add Authentication Source",
|
||||||
|
editInfo: "Modify Authentication Source",
|
||||||
|
delTip: "Confirm deleting the authentication source number [{num}] data item?",
|
||||||
|
delOk: "Deleted Successfully",
|
||||||
|
},
|
||||||
setting: {
|
setting: {
|
||||||
charMaxLen: 'characters length',
|
charMaxLen: 'characters length',
|
||||||
saveSubmit: 'Submit&Save',
|
saveSubmit: 'Submit&Save',
|
||||||
@@ -1830,6 +1878,10 @@ export default {
|
|||||||
home: 'Home Page',
|
home: 'Home Page',
|
||||||
homeTip:'Do you want to submit the current interface as the system interface?',
|
homeTip:'Do you want to submit the current interface as the system interface?',
|
||||||
homeSet:'Home Page Settings',
|
homeSet:'Home Page Settings',
|
||||||
|
backup: 'System Backup',
|
||||||
|
backupInstruction: 'System backup will back up the net element information records and configuration files running on the current system, and can restore the system to the previous state!',
|
||||||
|
backupExportTip: 'Confirm to export system backup?',
|
||||||
|
backupImportTip: 'Confirm to import system backup?',
|
||||||
},
|
},
|
||||||
role:{
|
role:{
|
||||||
allScopeOptions:'All data permissions',
|
allScopeOptions:'All data permissions',
|
||||||
@@ -1874,6 +1926,7 @@ export default {
|
|||||||
cancelGive:'Cancel authorization',
|
cancelGive:'Cancel authorization',
|
||||||
cancelSure:'Confirm to cancel the authorization of the data item with user number [{userId}]?',
|
cancelSure:'Confirm to cancel the authorization of the data item with user number [{userId}]?',
|
||||||
batchCancel:'Batch cancellation of authorization',
|
batchCancel:'Batch cancellation of authorization',
|
||||||
|
selectUser:'Assign Users',
|
||||||
},
|
},
|
||||||
dept:{
|
dept:{
|
||||||
classInfo:' Department Information',
|
classInfo:' Department Information',
|
||||||
@@ -1894,6 +1947,37 @@ export default {
|
|||||||
phone:'Contact Number',
|
phone:'Contact Number',
|
||||||
email:'Mail',
|
email:'Mail',
|
||||||
},
|
},
|
||||||
|
tenant:{
|
||||||
|
classInfo:' Tenant Information',
|
||||||
|
className:'Name',
|
||||||
|
classId:'Number',
|
||||||
|
classSort:'Sorting',
|
||||||
|
status:'Status',
|
||||||
|
type:' Tenancy Asset',
|
||||||
|
createTime:'Creation Time',
|
||||||
|
highClass:'Root Level',
|
||||||
|
key:'Asset Key',
|
||||||
|
emailTip:'Please input the correct email address',
|
||||||
|
phoneTip:'Please enter the correct phone number',
|
||||||
|
node:'Root Node',
|
||||||
|
delSure:'Are you sure to delete the data item with TenantName: {title}?',
|
||||||
|
delTypeSure:'Are you sure to delete the data item with Tenancy Asset: {tenancyAsset}, Asset Key: {tenancyKey}?',
|
||||||
|
open:'Exhibition',
|
||||||
|
close:'Fold',
|
||||||
|
addClass:'Add Tenant',
|
||||||
|
admin:'Principal',
|
||||||
|
phone:'Contact Number',
|
||||||
|
email:'Mail',
|
||||||
|
SDSST:'Network Slice',
|
||||||
|
APN:'Access Point Name',
|
||||||
|
IMSI:'SIM Card',
|
||||||
|
treeSelectTip:'Please select a tenant from the tenant list on the left for configuration',
|
||||||
|
upfTip:'Please select from the drop-down list of UPF Resource UIDs',
|
||||||
|
imsiTip:'Please select the matching type and fill in the SIM card number fragment',
|
||||||
|
radioTip:'Please select from the drop-down list of radio type and radio ID',
|
||||||
|
defaultTip:'Please select from the drop-down list of Tenancy Asset, and then fill the Asset Key',
|
||||||
|
patternTip:'The Asset Key cannot contain special characters',
|
||||||
|
},
|
||||||
post:{
|
post:{
|
||||||
positionInfo:'Position Information',
|
positionInfo:'Position Information',
|
||||||
positionId:'Position Number',
|
positionId:'Position Number',
|
||||||
@@ -1916,7 +2000,7 @@ export default {
|
|||||||
requestMe:'Request Method',
|
requestMe:'Request Method',
|
||||||
host:'Request Host',
|
host:'Request Host',
|
||||||
operStatus:'Status',
|
operStatus:'Status',
|
||||||
operDate:'Time',
|
operDate:'Time Stamp',
|
||||||
useTime:'Time Lap',
|
useTime:'Time Lap',
|
||||||
logInfo:'Operation Log Information',
|
logInfo:'Operation Log Information',
|
||||||
delSure:'Are you sure to delete the data item with access number [{ids}]?',
|
delSure:'Are you sure to delete the data item with access number [{ids}]?',
|
||||||
|
|||||||
@@ -10,13 +10,14 @@ export default {
|
|||||||
desc: '核心网管理平台',
|
desc: '核心网管理平台',
|
||||||
loading: '请稍等...',
|
loading: '请稍等...',
|
||||||
inputPlease: '请输入',
|
inputPlease: '请输入',
|
||||||
|
searchPlease: '搜索菜单...',
|
||||||
|
searchTip: '输入关键词搜索菜单',
|
||||||
selectPlease: '请选择',
|
selectPlease: '请选择',
|
||||||
tipTitle: '提示',
|
tipTitle: '提示',
|
||||||
msgSuccess: '{msg} 成功',
|
msgSuccess: '{msg} 成功',
|
||||||
errorFields: '请正确填写 {num} 处必填信息!',
|
errorFields: '请正确填写 {num} 处必填信息!',
|
||||||
tablePaginationTotal: '总共 {total} 条',
|
tablePaginationTotal: '总共 {total} 条',
|
||||||
noData: "暂无数据",
|
noData: "暂无数据",
|
||||||
zebra:'表格斑马纹',
|
|
||||||
ok: '确定',
|
ok: '确定',
|
||||||
cancel: '取消',
|
cancel: '取消',
|
||||||
close: '关闭',
|
close: '关闭',
|
||||||
@@ -29,6 +30,7 @@ export default {
|
|||||||
editText: '编辑',
|
editText: '编辑',
|
||||||
deleteText: '删除',
|
deleteText: '删除',
|
||||||
downloadText: '下载',
|
downloadText: '下载',
|
||||||
|
CloudServerText:'同步',
|
||||||
import:'导入',
|
import:'导入',
|
||||||
export:'导出',
|
export:'导出',
|
||||||
uploadText: '上传',
|
uploadText: '上传',
|
||||||
@@ -39,6 +41,10 @@ export default {
|
|||||||
columnSetText: '列设置',
|
columnSetText: '列设置',
|
||||||
columnSetTitle: '列展示/排序',
|
columnSetTitle: '列展示/排序',
|
||||||
sizeText: '密度',
|
sizeText: '密度',
|
||||||
|
exportCustom:'自定义导出',
|
||||||
|
exportColumns:'列定义',
|
||||||
|
resetToDefault:'重置为默认列',
|
||||||
|
exportDefault:'全部导出',
|
||||||
size: {
|
size: {
|
||||||
default: '默认',
|
default: '默认',
|
||||||
middle: '中等',
|
middle: '中等',
|
||||||
@@ -131,7 +137,7 @@ export default {
|
|||||||
},
|
},
|
||||||
LockScreen: {
|
LockScreen: {
|
||||||
inputPlacePwd:'请输入锁屏密码',
|
inputPlacePwd:'请输入锁屏密码',
|
||||||
validSucc:'校验通过',
|
enter:'进入',
|
||||||
validError:'校验失败',
|
validError:'校验失败',
|
||||||
backLogin:'退出并重新登录',
|
backLogin:'退出并重新登录',
|
||||||
backReload:'正在重启,请稍等...',
|
backReload:'正在重启,请稍等...',
|
||||||
@@ -143,7 +149,7 @@ export default {
|
|||||||
|
|
||||||
// 静态路由
|
// 静态路由
|
||||||
router: {
|
router: {
|
||||||
index: "主页",
|
index: "概览",
|
||||||
login: "登录",
|
login: "登录",
|
||||||
register: '注册',
|
register: '注册',
|
||||||
page403: '没有访问权限',
|
page403: '没有访问权限',
|
||||||
@@ -222,13 +228,12 @@ export default {
|
|||||||
capability: '用户容量',
|
capability: '用户容量',
|
||||||
serialNum: '序列号',
|
serialNum: '序列号',
|
||||||
expiryDate: '许可证到期日期',
|
expiryDate: '许可证到期日期',
|
||||||
neStatus:'网元状态异常',
|
neStatus:'状态异常',
|
||||||
runStatus:'运行状态',
|
runStatus:'运行状态',
|
||||||
mark:'简略信息',
|
mark:'信息',
|
||||||
object:'对象',
|
object:'对象',
|
||||||
versionNum:'版本号',
|
versionNum:'版本号',
|
||||||
systemStatus:'系统状态',
|
realNeStatus:'状态',
|
||||||
realNeStatus:'网元状态',
|
|
||||||
reloadTime:'刷新时间',
|
reloadTime:'刷新时间',
|
||||||
Critical:'严重告警',
|
Critical:'严重告警',
|
||||||
Major:'主要告警',
|
Major:'主要告警',
|
||||||
@@ -258,9 +263,13 @@ export default {
|
|||||||
registerBtn: '注册账号',
|
registerBtn: '注册账号',
|
||||||
loginBtn: '登录',
|
loginBtn: '登录',
|
||||||
loginSuccess: '登录成功',
|
loginSuccess: '登录成功',
|
||||||
loginMethod: '其他登录方式:',
|
otherMethod: '其他方式',
|
||||||
loginMethodWX: '微信扫一扫登录',
|
backBtn: '返回',
|
||||||
loginMethodQQ: 'QQ扫码登录',
|
backBtnLogin: '返回登录',
|
||||||
|
authorizedNotfound: '授权无效',
|
||||||
|
authorizedFailed: '授权失败',
|
||||||
|
authorizedSuccess: '授权成功',
|
||||||
|
redirectHome: '{i} 秒后跳转主页',
|
||||||
},
|
},
|
||||||
register: {
|
register: {
|
||||||
registerBtn: '注册',
|
registerBtn: '注册',
|
||||||
@@ -351,178 +360,39 @@ export default {
|
|||||||
description: "暂无数据,尝试刷新看看",
|
description: "暂无数据,尝试刷新看看",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
configManage: {
|
|
||||||
neManage: {
|
|
||||||
addNe:'添加网元',
|
|
||||||
delSure:'确认删除网元名称为{msg}的数据项 ',
|
|
||||||
editNe:'修改网元',
|
|
||||||
exportSure:'确认导出网元名称为 {msg} 的配置信息',
|
|
||||||
exportTip:'导出成功,请到备份管理进行下载',
|
|
||||||
getInfo:'获取网元信息失败',
|
|
||||||
neType:'网元类型',
|
|
||||||
neTypePlease: '请输入网元类型',
|
|
||||||
neId:'网元内部标识',
|
|
||||||
neName:'网元名称',
|
|
||||||
neTypeTip:'填写创建的网元类型,如:SMF',
|
|
||||||
uid:'资源唯一标识',
|
|
||||||
uidTip:'请输入资源唯一标识',
|
|
||||||
ip:'IP地址',
|
|
||||||
mac:'网元物理地址',
|
|
||||||
macTip:'能够定位网元的物理地址(MAC)',
|
|
||||||
port:'端口',
|
|
||||||
portTip:'最大范围0~65535',
|
|
||||||
pvflag:'网元虚拟化标识',
|
|
||||||
pnf:'物理网元',
|
|
||||||
vnf:'虚拟网元',
|
|
||||||
province:'网元服务省份',
|
|
||||||
vendorName:'厂商名称',
|
|
||||||
dn:'网络标识',
|
|
||||||
reload: '重载',
|
|
||||||
restart: '重启',
|
|
||||||
totalSure:'确认{oper}网元名称为 {msg} 的网元',
|
|
||||||
stop: '停止',
|
|
||||||
start: '启动',
|
|
||||||
log: '日志',
|
|
||||||
export: '导出',
|
|
||||||
import: '导入',
|
|
||||||
fileForm:'文件来源',
|
|
||||||
selectPlease:'请选择导入文件来源',
|
|
||||||
server:'服务器文件',
|
|
||||||
local:'本地文件',
|
|
||||||
fileSelect:'请选择当前导入文件',
|
|
||||||
sync:'同步到网元',
|
|
||||||
open:'开',
|
|
||||||
close:'关',
|
|
||||||
addFail:'新增失败',
|
|
||||||
operFail:'操作失败'
|
|
||||||
},
|
|
||||||
backupManage: {
|
|
||||||
setBackupTask: '设置自动备份时间',
|
|
||||||
neTypePlease: '查询网元类型',
|
|
||||||
neType: '网元类型',
|
|
||||||
neID: '网元内部标识',
|
|
||||||
fileName: '文件名',
|
|
||||||
createAt: '创建时间',
|
|
||||||
remark:'备份说明',
|
|
||||||
edit:'编辑备份文件',
|
|
||||||
totalSure:'确认{oper}记录编号为 {id} 的数据项?',
|
|
||||||
},
|
|
||||||
softwareManage: {
|
|
||||||
sendBtn: '下发',
|
|
||||||
runBtn: '激活',
|
|
||||||
backBtn: '回退',
|
|
||||||
historyBtn: '下发记录',
|
|
||||||
neTypePlease: '选择网元类型',
|
|
||||||
neType: '网元类型',
|
|
||||||
fileName: '文件名',
|
|
||||||
version: '版本号',
|
|
||||||
versionPlease: '版本号不能为空',
|
|
||||||
updateTime: '上传时间',
|
|
||||||
description: '功能描述',
|
|
||||||
deleteTip: '确认删除 【{fileName}】 的软件数据项?',
|
|
||||||
downloadTip: '确认下载 【{fileName}】 的软件数据项?',
|
|
||||||
updateComment: '软件说明',
|
|
||||||
updateCommentPlease: '请输入软件说明',
|
|
||||||
updateFile: '软件文件',
|
|
||||||
updateFilePlease: '请上传更新软件文件',
|
|
||||||
verifyFile: '校验文件',
|
|
||||||
selectFile: '选择文件',
|
|
||||||
sendTitle: '下发软件版本',
|
|
||||||
sendContent: '确认下发软件包为【{fileName}】的文件到对应网元?',
|
|
||||||
runTitle: '激活软件版本',
|
|
||||||
runContent: '确认在对应网元激活已下发【{fileName}】的软件版本?',
|
|
||||||
backTitle: '回退软件版本',
|
|
||||||
backContent: '确认在对应网元回退已下发【{fileName}】的软件版本?',
|
|
||||||
neId: '对应网元',
|
|
||||||
neIdPlease: '请选择对应网元',
|
|
||||||
versions:'版本',
|
|
||||||
upVersions:'升级前版本',
|
|
||||||
backVersions:'回退前版本',
|
|
||||||
status:'状态',
|
|
||||||
letUpTime:'激活时间',
|
|
||||||
createTime:'创建时间',
|
|
||||||
onlyAble:'只支持上传文件格式 {fileText}',
|
|
||||||
nullVersion:'当前网元无可回退版本',
|
|
||||||
},
|
|
||||||
license: {
|
|
||||||
neTypePlease: '选择网元类型',
|
|
||||||
neType: '网元类型',
|
|
||||||
serialNum: '序列号',
|
|
||||||
createTime: '时间',
|
|
||||||
comment: '说明',
|
|
||||||
updateComment: 'License说明',
|
|
||||||
updateCommentPlease: '请输入License说明',
|
|
||||||
updateFile: 'License文件',
|
|
||||||
updateFilePlease: '请上传更新License文件',
|
|
||||||
selectFile: '选择文件',
|
|
||||||
neId: '网元内部标识',
|
|
||||||
neIdPlease: '请选择对应网元',
|
|
||||||
},
|
|
||||||
configParam:{
|
|
||||||
dataNull:'暂无配置项数据',
|
|
||||||
editSuss:'修改成功',
|
|
||||||
editFail:'修改失败',
|
|
||||||
unable:'非法操作属性值',
|
|
||||||
delSure:'确认删除Index为 【{value}】 的数据项?',
|
|
||||||
addSuss:'新增成功',
|
|
||||||
addFail:'新增失败',
|
|
||||||
delArraySure:'确认删除{arrayChildTitle} Index 为 【{value}】 的数据项?',
|
|
||||||
parUnable:'参数值不在合理范围',
|
|
||||||
ipv4Tip:'不是合法的IPV4地址',
|
|
||||||
ipv6Tip:'不是合法的IPV6地址',
|
|
||||||
enumTip:'不是合理的枚举值',
|
|
||||||
boolTip:'不是合理的布尔类型的值',
|
|
||||||
default:'输入值是未知类型',
|
|
||||||
reloadSuss:'网元重新加载完成',
|
|
||||||
reloadFail:'网元重新加载失败',
|
|
||||||
neNUll:'暂无网元列表数据',
|
|
||||||
reload:'重载',
|
|
||||||
post:'提交',
|
|
||||||
editSure:'确认更新该属性值吗?',
|
|
||||||
arraryEdit:'确认提交更新 Index 为 【{value}】 的记录吗?',
|
|
||||||
addSure:'确认提交新增 Index :【{value}】 的记录吗?',
|
|
||||||
},
|
|
||||||
configParamForm: {
|
|
||||||
treeTitle: "配置导航",
|
|
||||||
treeSelectTip: "左侧配置导航中选择配置项信息!",
|
|
||||||
neType: "网元类型",
|
|
||||||
neTypePleace: "请选择网元类型",
|
|
||||||
noConfigData: "暂无配置项数据",
|
|
||||||
updateValue: "【 {num} 】 属性值修改成功",
|
|
||||||
updateValueErr: "属性值修改失败",
|
|
||||||
updateItem: "修改 Index 为 {num} 记录成功",
|
|
||||||
updateItemErr: "记录修改失败",
|
|
||||||
delItemOk: "删除 Index 为 {num} 记录成功",
|
|
||||||
addItemOk: "新增 Index 为 {num} 记录成功",
|
|
||||||
addItemErr: "记录新增失败",
|
|
||||||
requireUn: "【 {display} 】输入值是未知类型",
|
|
||||||
requireString: "【 {display} 】参数值不合理",
|
|
||||||
requireInt: "【 {display} 】参数值不在合理范围 {filter}",
|
|
||||||
requireIpv4: "【 {display} 】不是合法的IPV4地址",
|
|
||||||
requireIpv6: "【 {display} 】不是合法的IPV6地址",
|
|
||||||
requireEnum: "【 {display} 】不是合理的枚举值",
|
|
||||||
requireBool: "【 {display} 】不是合理的布尔类型的值",
|
|
||||||
editOkTip: "确认更新该【 {num} 】属性值吗?",
|
|
||||||
updateItemTip: "确认更新Index为 【{num}】 的数据项?",
|
|
||||||
delItemTip: "确认删除Index为 【{num}】 的数据项?",
|
|
||||||
arrayMore: "展开",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
dashboard: {
|
dashboard: {
|
||||||
overview:{
|
overview:{
|
||||||
title: "核心网系统看板",
|
title: "核心网系统看板",
|
||||||
fullscreen: "点击全屏显示",
|
fullscreen: "点击全屏显示",
|
||||||
toRouter: "点击跳转详情页面",
|
toRouter: "点击跳转详情页面",
|
||||||
|
Users:"UDM 订阅数据",
|
||||||
|
VoNR:"IMS在线用户",
|
||||||
|
sessions:"SMF的PDU会话",
|
||||||
|
FivegNodeN:"5G在线基站数",
|
||||||
|
Fiveusers:"AMF在线用户数",
|
||||||
|
FourgNodeN:"4G在线基站数",
|
||||||
|
Fourusers:"MME在线用户数",
|
||||||
|
UPFjump:"点击跳转到UPF黄金指标界面",
|
||||||
|
Networkjump:"点击跳转到网元系统拓扑图",
|
||||||
|
Alarmjump:"点击跳转到活动告警",
|
||||||
|
IMSUsers:"点击跳转到 IMS 用户",
|
||||||
|
VoIPUsers:"点击跳转到 VoIP 用户",
|
||||||
skim: {
|
skim: {
|
||||||
users: "用户数",
|
users: "用户数",
|
||||||
userTitle:'用户信息',
|
userTitle:'用户信息',
|
||||||
imsUeNum: "IMS 会话数",
|
imsUeNum: "IMS 会话数",
|
||||||
smfUeNum: "Data 会话数",
|
smfUeNum: "Data 会话数",
|
||||||
gnbBase: "5G 基站数",
|
gnbBase: "5G 基站数",
|
||||||
|
gnbSumBase: "5G 基站总数",
|
||||||
gnbUeNum:'5G 用户数',
|
gnbUeNum:'5G 用户数',
|
||||||
enbBase: "4G 基站数",
|
enbBase: "4G 基站数",
|
||||||
|
enbSumBase: "4G 基站总数",
|
||||||
enbUeNum:'4G 用户数',
|
enbUeNum:'4G 用户数',
|
||||||
baseTitle:'在线信息',
|
baseTitle:'在线信息',
|
||||||
|
nodeBInfo: '基站信息',
|
||||||
|
onlineinfo:'User Online Infomation',
|
||||||
|
ims:'IMS',
|
||||||
|
voip:'VoIP'
|
||||||
},
|
},
|
||||||
upfFlow:{
|
upfFlow:{
|
||||||
title: "用户面吞吐量",
|
title: "用户面吞吐量",
|
||||||
@@ -552,6 +422,7 @@ export default {
|
|||||||
},
|
},
|
||||||
userActivity: {
|
userActivity: {
|
||||||
title: "用户活动",
|
title: "用户活动",
|
||||||
|
imsTitle: "IMS 活动",
|
||||||
type: "类型",
|
type: "类型",
|
||||||
duration: "时长",
|
duration: "时长",
|
||||||
caller: "主叫",
|
caller: "主叫",
|
||||||
@@ -570,23 +441,32 @@ export default {
|
|||||||
rowInfo: "记录信息",
|
rowInfo: "记录信息",
|
||||||
type: "记录类型",
|
type: "记录类型",
|
||||||
duration: "通话时长",
|
duration: "通话时长",
|
||||||
|
mosAverage: "MOS",
|
||||||
|
callConnectionTime: "Call Connection Time",
|
||||||
seizureTime: "呼叫开始时间",
|
seizureTime: "呼叫开始时间",
|
||||||
releaseTime: "挂断结束时间",
|
releaseTime: "挂断结束时间",
|
||||||
caller: "主叫",
|
caller: "主叫",
|
||||||
called: "被叫",
|
called: "被叫",
|
||||||
result: "结果",
|
result: "结果",
|
||||||
|
resultCode: "结果码",
|
||||||
|
resultCause: "结果原因",
|
||||||
resultOk: "成功",
|
resultOk: "成功",
|
||||||
resultFail: "失败",
|
resultFail: "失败",
|
||||||
delTip: "确认删除编号为【{msg}】的数据项?",
|
delTip: "确认删除编号为【{msg}】的数据项?",
|
||||||
exportTip: "确认导出当前查询条件的话单数据吗?(导出最大支持一万条)",
|
tenantName: "租户名称",
|
||||||
smfChargingID: '计费ID',
|
exportTip: "确认导出当前查询条件的话单数据吗?",
|
||||||
|
chargingID: '计费ID',
|
||||||
smfSubscriptionIDData: '订阅 ID 数据',
|
smfSubscriptionIDData: '订阅 ID 数据',
|
||||||
smfSubscriptionIDType: '订阅 ID 类型',
|
smfSubscriptionIDType: '订阅 ID 类型',
|
||||||
smfDataVolumeUplink: '数据量上行链路',
|
smfDataVolumeUplink: '数据量上行链路',
|
||||||
smfDataVolumeDownlink: '数据量下行链路',
|
smfDataVolumeDownlink: '数据量下行链路',
|
||||||
smfDataTotalVolume: '数据总量',
|
smfDataTotalVolume: '数据总量',
|
||||||
smfDuration: '持续时间',
|
durationTime: '持续时间',
|
||||||
smfInvocationTime: '调用时间',
|
invocationTime: '调用时间',
|
||||||
|
sgwcServedIMSI: 'IMSI',
|
||||||
|
sgwcServedMSISDN: 'MSISDN',
|
||||||
|
sgwcVolumeGPRSUplink: 'GPRS 上行链路',
|
||||||
|
sgwcVolumeGPRSDownlink: 'GPRS 下行链路',
|
||||||
},
|
},
|
||||||
ue: {
|
ue: {
|
||||||
eventType: "事件类型",
|
eventType: "事件类型",
|
||||||
@@ -598,7 +478,7 @@ export default {
|
|||||||
result: "结果",
|
result: "结果",
|
||||||
resultOk: "成功",
|
resultOk: "成功",
|
||||||
delTip: "确认删除编号为【{msg}】的数据项?",
|
delTip: "确认删除编号为【{msg}】的数据项?",
|
||||||
exportTip: "确认导出当前查询条件的事件数据吗?(导出最大支持一万条)",
|
exportTip: "确认导出当前查询条件的事件数据吗?",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
ne: {
|
ne: {
|
||||||
@@ -621,6 +501,8 @@ export default {
|
|||||||
portTip: "网元服务端口,默认:33030",
|
portTip: "网元服务端口,默认:33030",
|
||||||
serialNum: '序列号',
|
serialNum: '序列号',
|
||||||
expiryDate: '许可证到期日期',
|
expiryDate: '许可证到期日期',
|
||||||
|
ueNumber: '用户数',
|
||||||
|
nbNumber: '基站数',
|
||||||
normalcy: '正常',
|
normalcy: '正常',
|
||||||
exceptions: '异常',
|
exceptions: '异常',
|
||||||
restart: '重启',
|
restart: '重启',
|
||||||
@@ -658,7 +540,7 @@ export default {
|
|||||||
delTip: '确认删除网元信息数据项吗?',
|
delTip: '确认删除网元信息数据项吗?',
|
||||||
oam: {
|
oam: {
|
||||||
title: 'OAM配置',
|
title: 'OAM配置',
|
||||||
sync: '同步到网元',
|
restart: '下发后重启网元',
|
||||||
oamEnable: '服务',
|
oamEnable: '服务',
|
||||||
oamPort: '端口',
|
oamPort: '端口',
|
||||||
snmpEnable: '服务',
|
snmpEnable: '服务',
|
||||||
@@ -761,14 +643,15 @@ export default {
|
|||||||
upgradeDone: '更新完成,服务正在重载',
|
upgradeDone: '更新完成,服务正在重载',
|
||||||
upgradeFail: '更新失败,请检查软件文件是否存在且服务终端环境是否可用!',
|
upgradeFail: '更新失败,请检查软件文件是否存在且服务终端环境是否可用!',
|
||||||
upgradeModal: '网元版本更新',
|
upgradeModal: '网元版本更新',
|
||||||
|
noPath: '软件包文件未发现',
|
||||||
},
|
},
|
||||||
neLicense: {
|
neLicense: {
|
||||||
status: "许可证状态",
|
status: "许可证状态",
|
||||||
change: "变更许可证",
|
change: "变更许可证",
|
||||||
reload: "刷新信息",
|
reload: "刷新信息",
|
||||||
reloadTip: "确认要刷新许可证信息吗?",
|
reloadTip: "确认要刷新许可证信息吗?",
|
||||||
reloadBatch: "批量刷新",
|
reloadBatch: "刷新许可证状态",
|
||||||
reloadBatchTip: "对勾选的记录进行信息刷新吗?",
|
reloadBatchTip: "对当前列表网元进行许可证状态信息刷新吗?",
|
||||||
updateTtile: "更新许可证",
|
updateTtile: "更新许可证",
|
||||||
downCodeTop: "确认要将许可激活码保存到文件吗?",
|
downCodeTop: "确认要将许可激活码保存到文件吗?",
|
||||||
activationRequestCode: "许可激活码",
|
activationRequestCode: "许可激活码",
|
||||||
@@ -784,7 +667,9 @@ export default {
|
|||||||
treeSelectTip: "左侧配置导航中选择配置项信息!",
|
treeSelectTip: "左侧配置导航中选择配置项信息!",
|
||||||
neType: "网元类型",
|
neType: "网元类型",
|
||||||
neTypePleace: "请选择网元类型",
|
neTypePleace: "请选择网元类型",
|
||||||
|
neIdSyncPleace: "请选择同步网元",
|
||||||
noConfigData: "暂无配置项数据",
|
noConfigData: "暂无配置项数据",
|
||||||
|
noConfigdDisabled: "配置项网元未正常服务",
|
||||||
updateValue: "【 {num} 】 属性值修改成功",
|
updateValue: "【 {num} 】 属性值修改成功",
|
||||||
updateValueErr: "属性值修改失败",
|
updateValueErr: "属性值修改失败",
|
||||||
updateItem: "修改 Index 为 {num} 记录成功",
|
updateItem: "修改 Index 为 {num} 记录成功",
|
||||||
@@ -808,6 +693,19 @@ export default {
|
|||||||
name: "名称",
|
name: "名称",
|
||||||
downTip: '确认要下载备份文件【{txt}】吗?',
|
downTip: '确认要下载备份文件【{txt}】吗?',
|
||||||
title: "修改备份信息 {txt}",
|
title: "修改备份信息 {txt}",
|
||||||
|
backupModal: {
|
||||||
|
pushFileOper: "将当前文件发送到远程备份",
|
||||||
|
title: "设置远程备份服务",
|
||||||
|
enable: "启用",
|
||||||
|
toIp: "服务IP",
|
||||||
|
toIpPleace: "请输入远程备份服务器 IP 地址",
|
||||||
|
toPort: "服务端口",
|
||||||
|
username: "登录用户名",
|
||||||
|
usernamePleace: '请输入服务登录用户名',
|
||||||
|
password: "登录密码",
|
||||||
|
dir: "保存目录",
|
||||||
|
dirPleace: '请输入服务地址目标文件目录',
|
||||||
|
}
|
||||||
},
|
},
|
||||||
neQuickSetup: {
|
neQuickSetup: {
|
||||||
reloadPara5G: '刷新',
|
reloadPara5G: '刷新',
|
||||||
@@ -858,6 +756,58 @@ export default {
|
|||||||
licenseTip2: '2. 点击【结束】将结束安装过程',
|
licenseTip2: '2. 点击【结束】将结束安装过程',
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
neData: {
|
||||||
|
common: {
|
||||||
|
startIMSI: '起始IMSI',
|
||||||
|
imsi: 'IMSI',
|
||||||
|
imsiTip: 'IMSI=MCC+MNC+MSIN',
|
||||||
|
imsiTip1: 'MCC=移动国家号码, 由三位数字组成',
|
||||||
|
imsiTip2: 'MNC=移动网络号,由两位数字组成',
|
||||||
|
imsiTip3: 'MSIN=移动客户识别码,采用等长10位数字构成',
|
||||||
|
imsiPlease: "请正确输入IMSI",
|
||||||
|
msisdn: '移动客户识别码',
|
||||||
|
msisdnPlease: "请正确输入移动客户识别码",
|
||||||
|
loadDataConfirm: '确认要重新加载数据吗?',
|
||||||
|
loadData: '加载数据',
|
||||||
|
loadDataTip: '成功获取加载数据:{num}条,系统内部正在进行数据更新,大约需要{timer}秒,请稍候!!!',
|
||||||
|
batchOper: '批量操作',
|
||||||
|
batchAddText: '批量新增',
|
||||||
|
batchDelText: '批量删除',
|
||||||
|
batchUpdateText: '批量更新',
|
||||||
|
batchNum: '批量个数',
|
||||||
|
checkDel:'勾选删除',
|
||||||
|
importTemplate: '导入模板',
|
||||||
|
},
|
||||||
|
baseStation: {
|
||||||
|
list: "列表",
|
||||||
|
topology: "拓扑图",
|
||||||
|
nbName: "设备名称",
|
||||||
|
nbId: "设备ID",
|
||||||
|
ueNum: "在线用户数",
|
||||||
|
topologyTitle: "基站状态关系图",
|
||||||
|
name: "基站名称",
|
||||||
|
namePlease: "文本内容长度0~64",
|
||||||
|
position: "基站位置",
|
||||||
|
positionPlease: "位置描述。禁止空格,文本内容长度0-64",
|
||||||
|
address: "IP地址",
|
||||||
|
addressPlease: "文本内容长度0~64",
|
||||||
|
state: "基站状态",
|
||||||
|
online: "在线",
|
||||||
|
offline: "离线",
|
||||||
|
time: "变更时间",
|
||||||
|
addRadio: "添加基站信息",
|
||||||
|
editRadio: "更新基站信息",
|
||||||
|
history: "历史记录",
|
||||||
|
exportTip: "确认根据搜索条件导出xlsx表格文件吗?",
|
||||||
|
importDataEmpty: "导入数据为空",
|
||||||
|
},
|
||||||
|
backupData: {
|
||||||
|
auth: "UDM鉴权用户",
|
||||||
|
sub: "UDM签约用户",
|
||||||
|
voip: "VOIP鉴权用户",
|
||||||
|
volte: "IMS签约用户",
|
||||||
|
}
|
||||||
|
},
|
||||||
neUser: {
|
neUser: {
|
||||||
auth: {
|
auth: {
|
||||||
authInfo:'鉴权信息',
|
authInfo:'鉴权信息',
|
||||||
@@ -868,6 +818,7 @@ export default {
|
|||||||
checkExport : '勾选导出',
|
checkExport : '勾选导出',
|
||||||
checkExportConfirm: '确认导出已勾选的鉴权用户数据吗?',
|
checkExportConfirm: '确认导出已勾选的鉴权用户数据吗?',
|
||||||
import: '导入',
|
import: '导入',
|
||||||
|
importFail: '失败记录',
|
||||||
loadDataConfirm: '确认要重新加载数据吗?',
|
loadDataConfirm: '确认要重新加载数据吗?',
|
||||||
loadData: '加载数据',
|
loadData: '加载数据',
|
||||||
loadDataTip: '成功获取加载数据:{num}条,系统内部正在进行数据更新,大约需要{timer}秒,请稍候!!!',
|
loadDataTip: '成功获取加载数据:{num}条,系统内部正在进行数据更新,大约需要{timer}秒,请稍候!!!',
|
||||||
@@ -887,15 +838,18 @@ export default {
|
|||||||
opcTip: '鉴权秘钥,OPC是由Ki和OP经过计算得来的,OP为运营商的根秘钥,ki是鉴权秘钥,最大长度为32',
|
opcTip: '鉴权秘钥,OPC是由Ki和OP经过计算得来的,OP为运营商的根秘钥,ki是鉴权秘钥,最大长度为32',
|
||||||
delSure:'确认删除IMSI编号为: {imsi} 的用户吗?',
|
delSure:'确认删除IMSI编号为: {imsi} 的用户吗?',
|
||||||
imsiConfirm:'IMSI的长度必须为15',
|
imsiConfirm:'IMSI的长度必须为15',
|
||||||
|
startUserName:'起始用户名',
|
||||||
},
|
},
|
||||||
sub: {
|
sub: {
|
||||||
subInfo:'签约信息',
|
subInfo:'签约信息',
|
||||||
neType: 'UDM网元类型',
|
neType: 'UDM网元类型',
|
||||||
|
imsType:'IMS网元类型',
|
||||||
export: '导出',
|
export: '导出',
|
||||||
exportConfirm: '确认导出全部签约用户数据吗?',
|
exportConfirm: '确认导出全部签约用户数据吗?',
|
||||||
checkExport : '勾选导出',
|
checkExport : '勾选导出',
|
||||||
checkExportConfirm: '确认导出已勾选的签约用户数据吗?',
|
checkExportConfirm: '确认导出已勾选的签约用户数据吗?',
|
||||||
import: '导入',
|
import: '导入',
|
||||||
|
importFail: '失败记录',
|
||||||
loadDataConfirm: '确认要重新加载数据吗?',
|
loadDataConfirm: '确认要重新加载数据吗?',
|
||||||
loadData: '加载数据',
|
loadData: '加载数据',
|
||||||
loadDataTip: '成功获取加载数据:{num}条,系统内部正在进行数据更新,大约需要{timer}秒,请稍候!!!',
|
loadDataTip: '成功获取加载数据:{num}条,系统内部正在进行数据更新,大约需要{timer}秒,请稍候!!!',
|
||||||
@@ -919,6 +873,10 @@ export default {
|
|||||||
rfspTip:'RFSP 索引,在 NG-RAN 中,特定 RRM 配置的索引,参数介于0到127之间',
|
rfspTip:'RFSP 索引,在 NG-RAN 中,特定 RRM 配置的索引,参数介于0到127之间',
|
||||||
ueTypeTip: '运营商定义的用户 UE Usage Type,整型,参数介于0到127之间',
|
ueTypeTip: '运营商定义的用户 UE Usage Type,整型,参数介于0到127之间',
|
||||||
cnFlag: '是否开启 5G Core Network 服务',
|
cnFlag: '是否开启 5G Core Network 服务',
|
||||||
|
cnFlag0: '不允许接入',
|
||||||
|
cnFlag1: '只能接入 5G',
|
||||||
|
cnFlag2: '只能接入 4G',
|
||||||
|
cnFlag3: '允许接入 4G/5G',
|
||||||
epsFlagTip: '是否开启 4G EPS 服务',
|
epsFlagTip: '是否开启 4G EPS 服务',
|
||||||
contextIdTip: '签约APN 上下文ID,必须从APN Context list 中选择。',
|
contextIdTip: '签约APN 上下文ID,必须从APN Context list 中选择。',
|
||||||
apnContextTip: '手机可用的APN列表,最多六个,在HSS中定义。',
|
apnContextTip: '手机可用的APN列表,最多六个,在HSS中定义。',
|
||||||
@@ -928,6 +886,12 @@ export default {
|
|||||||
ardTip:'接入控制标志(Access-Restriction-Data),可用于区分2G/3G/LTE用户,便于为2G/3G/LTE网络共存时,对不同类型用户进行区分服务',
|
ardTip:'接入控制标志(Access-Restriction-Data),可用于区分2G/3G/LTE用户,便于为2G/3G/LTE网络共存时,对不同类型用户进行区分服务',
|
||||||
smDataTip:'sm_data=1-000001&internet-1.2.3.4&ims-1.2.3.5中的IP:1.2.3.4为5G用户internet这个APN分配的静态IP,1.2.3.5为5G用户ims这个APN分配的静态IP。如果是动态分配,把IP以及前面一个连接符去掉即可。需支持多个dnn用&连接',
|
smDataTip:'sm_data=1-000001&internet-1.2.3.4&ims-1.2.3.5中的IP:1.2.3.4为5G用户internet这个APN分配的静态IP,1.2.3.5为5G用户ims这个APN分配的静态IP。如果是动态分配,把IP以及前面一个连接符去掉即可。需支持多个dnn用&连接',
|
||||||
smDataArrTip:'SST,DNN/APN为必填项',
|
smDataArrTip:'SST,DNN/APN为必填项',
|
||||||
|
tenantName:'租户名称',
|
||||||
|
imsiMode:'IMSI匹配模式',
|
||||||
|
fuzzyMatch:'模糊匹配',
|
||||||
|
prefixMatch:'前缀匹配',
|
||||||
|
fullMatch:'全匹配',
|
||||||
|
suffixMatch:'后缀匹配',
|
||||||
},
|
},
|
||||||
pcf: {
|
pcf: {
|
||||||
neType: 'PCF网元对象',
|
neType: 'PCF网元对象',
|
||||||
@@ -962,6 +926,8 @@ export default {
|
|||||||
},
|
},
|
||||||
base5G: {
|
base5G: {
|
||||||
neType: '网元对象',
|
neType: '网元对象',
|
||||||
|
gnb:'5G 基站',
|
||||||
|
enb:'4G 基站',
|
||||||
},
|
},
|
||||||
n3iwf: {
|
n3iwf: {
|
||||||
neType: 'N3IWF网元对象',
|
neType: 'N3IWF网元对象',
|
||||||
@@ -974,7 +940,7 @@ export default {
|
|||||||
},
|
},
|
||||||
nssf:{
|
nssf:{
|
||||||
neType: 'NSSF网元对象',
|
neType: 'NSSF网元对象',
|
||||||
},
|
}
|
||||||
},
|
},
|
||||||
perfManage: {
|
perfManage: {
|
||||||
taskManage:{
|
taskManage:{
|
||||||
@@ -1073,8 +1039,13 @@ export default {
|
|||||||
expression:'计算公式',
|
expression:'计算公式',
|
||||||
description:'描述',
|
description:'描述',
|
||||||
kpiSet:'统计设置',
|
kpiSet:'统计设置',
|
||||||
sixHoursAgo:'6小时前',
|
ago1Hour:'过去1小时',
|
||||||
threeHoursAgo:'3小时前',
|
ago3Hour:'过去3小时',
|
||||||
|
ago6Hour:'过去6小时',
|
||||||
|
toDay:'今天',
|
||||||
|
ago1Day:'过去1天',
|
||||||
|
ago7Day:'过去7天',
|
||||||
|
ago15Day:'过去15天',
|
||||||
delCustomTip:'确认删除自定义指标项为 {num} 的数据项?',
|
delCustomTip:'确认删除自定义指标项为 {num} 的数据项?',
|
||||||
delCustom:'成功删除记录编号为 {num} 自定义指标',
|
delCustom:'成功删除记录编号为 {num} 自定义指标',
|
||||||
addCustom:'添加自定义指标',
|
addCustom:'添加自定义指标',
|
||||||
@@ -1090,6 +1061,12 @@ export default {
|
|||||||
expressionModal:'表达式模块',
|
expressionModal:'表达式模块',
|
||||||
expressionErrorTip:'请检查表达式,错误的指标为{kpiId}',
|
expressionErrorTip:'请检查表达式,错误的指标为{kpiId}',
|
||||||
expressionNoIdTip:'请检查表达式,没有找到任何有效的指标',
|
expressionNoIdTip:'请检查表达式,没有找到任何有效的指标',
|
||||||
|
unitSelect:'为更好展示图需选择相同单位,当前单位为:',
|
||||||
|
avg:'(平均)',
|
||||||
|
total:'(累计)',
|
||||||
|
ago1:'近1天值',
|
||||||
|
ago7:'近7天值',
|
||||||
|
ago30:'近30天值',
|
||||||
},
|
},
|
||||||
kpiKeyTarget:{
|
kpiKeyTarget:{
|
||||||
"time":"时间",
|
"time":"时间",
|
||||||
@@ -1109,34 +1086,37 @@ export default {
|
|||||||
kpiOverView:{
|
kpiOverView:{
|
||||||
"kpiName":"指标名",
|
"kpiName":"指标名",
|
||||||
"maxValue":"最大值",
|
"maxValue":"最大值",
|
||||||
|
"maxValueTip":"用户筛选时间范围内度量数据的最大值。",
|
||||||
"minValue":"最小值",
|
"minValue":"最小值",
|
||||||
|
"minValueTip":"用户筛选时间范围内度量数据的最小值。",
|
||||||
|
"avgValue":"平均值",
|
||||||
|
"avgValueTip":"用户筛选时间范围内度量数据的平均值。",
|
||||||
|
"totalValue":"总值",
|
||||||
|
"totalValueTip":"用户筛选时间范围内度量数据的总值。",
|
||||||
"kpiChartTitle":"网元指标概览",
|
"kpiChartTitle":"网元指标概览",
|
||||||
"changeLine":"切换为折线图",
|
"changeLine":"切换为折线图",
|
||||||
"changeBar":"切换为柱状图",
|
"changeBar":"切换为柱状图",
|
||||||
"chooseShowMetrics":"选择需要显示的指标",
|
"chooseShowMetrics":"选择需要显示的指标",
|
||||||
"chooseMetrics":"选择指标",
|
"chooseMetrics":"选择指标",
|
||||||
|
"tips":"百分比和比率是平均值,计数是统计值。",
|
||||||
|
},
|
||||||
|
voiceOverView:{
|
||||||
|
"voiceTitle":"语音通话仪表盘",
|
||||||
|
"tips":"每分钟数据语音统计",
|
||||||
|
"ne":"网元",
|
||||||
|
"now":"现在",
|
||||||
|
"last":"过去",
|
||||||
|
"calls":"呼叫",
|
||||||
|
"activeCall":"正在通话",
|
||||||
|
"callMOMT":"呼叫 主叫接通率/被叫接通率",
|
||||||
|
"failedcall":"失败呼叫",
|
||||||
|
"registration":"注册",
|
||||||
|
"activeregistration":"主动注册",
|
||||||
|
"registrationsuccess":"注册成功率",
|
||||||
|
"failedregistration":"失败注册",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
traceManage: {
|
traceManage: {
|
||||||
analysis: {
|
|
||||||
imsi: 'IMSI',
|
|
||||||
imsiPlease: '请输入IMSI',
|
|
||||||
msisdn: 'MSISDN',
|
|
||||||
msisdnPlease: '请输入MSISDN',
|
|
||||||
trackTaskId: '跟踪任务标记',
|
|
||||||
srcIp: '源IP地址',
|
|
||||||
dstIp: '目标IP地址',
|
|
||||||
signalType: '信令类型',
|
|
||||||
msgDirect: '消息元',
|
|
||||||
msgType: '消息类型',
|
|
||||||
rowTime: '记录时间',
|
|
||||||
signalData: '信令数据',
|
|
||||||
signalDetail: '信令详情',
|
|
||||||
noData: '无信息内容',
|
|
||||||
taskTitle: '任务 {num}',
|
|
||||||
taskDownText: '下载HTML',
|
|
||||||
taskDownTip: '确认下载信令详情HTML文件?',
|
|
||||||
},
|
|
||||||
pcap: {
|
pcap: {
|
||||||
capArgPlease: '请输入tcpdump -i any支持参数',
|
capArgPlease: '请输入tcpdump -i any支持参数',
|
||||||
cmd: '命令',
|
cmd: '命令',
|
||||||
@@ -1171,6 +1151,7 @@ export default {
|
|||||||
},
|
},
|
||||||
task: {
|
task: {
|
||||||
traceId: '跟踪编号',
|
traceId: '跟踪编号',
|
||||||
|
title: '跟踪标题',
|
||||||
trackType: '跟踪类型',
|
trackType: '跟踪类型',
|
||||||
trackTypePlease: '请选择跟踪类型',
|
trackTypePlease: '请选择跟踪类型',
|
||||||
creater: '创建人',
|
creater: '创建人',
|
||||||
@@ -1187,21 +1168,17 @@ export default {
|
|||||||
imsiTip: '移动通信IMSI编号',
|
imsiTip: '移动通信IMSI编号',
|
||||||
srcIp: '源IP地址',
|
srcIp: '源IP地址',
|
||||||
srcIpPlease: '请输入源IP地址',
|
srcIpPlease: '请输入源IP地址',
|
||||||
srcIpTip: '当前发送端IPv4地址',
|
srcIpTip: '发送端IPv4地址',
|
||||||
dstIp: '目标IP地址',
|
dstIp: '目标IP地址',
|
||||||
dstIpPlease: '请输入目标IP地址',
|
dstIpPlease: '请输入目标IP地址',
|
||||||
dstIpTip: '对方接收端IPv4地址',
|
dstIpTip: '接收端IPv4地址',
|
||||||
interfaces: '信令接口',
|
interfaces: '信令接口',
|
||||||
interfacesPlease: '请输入信令接口',
|
interfacesPlease: '请输入信令接口',
|
||||||
signalPort: '信令端口',
|
rangePicker: '任务时间',
|
||||||
signalPortPlease: '请输入信令端口',
|
|
||||||
signalPortTip: '目标IP地址或源IP地址对应一方的端口',
|
|
||||||
rangePicker: '开始结束时间',
|
|
||||||
rangePickerPlease: '请选择任务时间开始结束时间',
|
rangePickerPlease: '请选择任务时间开始结束时间',
|
||||||
remark: '说明',
|
remark: '说明',
|
||||||
remarkPlease: '可输入任务说明',
|
remarkPlease: '可输入任务说明',
|
||||||
addTask: '添加任务',
|
addTask: '添加任务',
|
||||||
editTask: '修改任务',
|
|
||||||
viewTask: '查看任务',
|
viewTask: '查看任务',
|
||||||
errorTaskInfo: '获取任务信息失败',
|
errorTaskInfo: '获取任务信息失败',
|
||||||
delTaskTip: '确认删除记录编号为 {id} 的数据项?',
|
delTaskTip: '确认删除记录编号为 {id} 的数据项?',
|
||||||
@@ -1211,6 +1188,15 @@ export default {
|
|||||||
traceFile: "跟踪文件",
|
traceFile: "跟踪文件",
|
||||||
errMsg: "错误信息",
|
errMsg: "错误信息",
|
||||||
imsiORmsisdn: "imsi 或 msisdn 是空值,不能开始任务",
|
imsiORmsisdn: "imsi 或 msisdn 是空值,不能开始任务",
|
||||||
|
dataView: "跟踪数据",
|
||||||
|
protocolOrInterface: "协议/接口",
|
||||||
|
msgNe: '消息网元',
|
||||||
|
msgEvent: '消息事件',
|
||||||
|
msgType: '消息类型',
|
||||||
|
msgDirect: '消息方向',
|
||||||
|
msgLen: '消息长度',
|
||||||
|
rowTime: '消息时间',
|
||||||
|
taskInfo: '任务信息',
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
faultManage: {
|
faultManage: {
|
||||||
@@ -1320,6 +1306,7 @@ export default {
|
|||||||
size: "文件大小",
|
size: "文件大小",
|
||||||
modifiedTime: "修改时间",
|
modifiedTime: "修改时间",
|
||||||
fileName: "文件名称",
|
fileName: "文件名称",
|
||||||
|
downTipZip: "确认将目录 【{fileName}】 下载为ZIP文件?",
|
||||||
downTip: "确认下载文件名为 【{fileName}】 文件?",
|
downTip: "确认下载文件名为 【{fileName}】 文件?",
|
||||||
downTipErr: "文件获取失败",
|
downTipErr: "文件获取失败",
|
||||||
dirCd: "进入目录",
|
dirCd: "进入目录",
|
||||||
@@ -1330,12 +1317,19 @@ export default {
|
|||||||
tailLines: '末尾行数',
|
tailLines: '末尾行数',
|
||||||
},
|
},
|
||||||
exportFile:{
|
exportFile:{
|
||||||
fileName:'文件来源',
|
fileSource:'文件来源',
|
||||||
|
fileSourcePlease:'请选择文件来源',
|
||||||
downTip: "确认下载文件名为 【{fileName}】 文件?",
|
downTip: "确认下载文件名为 【{fileName}】 文件?",
|
||||||
downTipErr: "文件获取失败",
|
downTipErr: "文件获取失败",
|
||||||
deleteTip: "确认删除文件名为 【{fileName}】 文件?",
|
deleteTip: "确认删除文件名为 【{fileName}】 文件?",
|
||||||
deleteTipErr: "文件删除失败",
|
deleteTipErr: "文件删除失败",
|
||||||
selectTip:"请选择文件名",
|
sysloginLog:'系统登录日志',
|
||||||
|
sysOperateLog:'系统操作日志',
|
||||||
|
neLog:'网元日志',
|
||||||
|
cdrIMS:'语音话单',
|
||||||
|
cdrSMF:'数据话单',
|
||||||
|
cdrSMSC:'短信话单',
|
||||||
|
cdrSGWC:'漫游数据话单',
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
monitor: {
|
monitor: {
|
||||||
@@ -1707,8 +1701,10 @@ export default {
|
|||||||
userNum: '用户编号',
|
userNum: '用户编号',
|
||||||
account: '登录账号',
|
account: '登录账号',
|
||||||
userName: '用户昵称',
|
userName: '用户昵称',
|
||||||
permission: '用户权限',
|
permission: '用户角色',
|
||||||
className: '部门名称',
|
className: '部门名称',
|
||||||
|
userType: '用户类型',
|
||||||
|
tenntName:'租户名称',
|
||||||
loginIp: '登录地址',
|
loginIp: '登录地址',
|
||||||
loginTime: '登录时间',
|
loginTime: '登录时间',
|
||||||
status: '用户状态',
|
status: '用户状态',
|
||||||
@@ -1734,6 +1730,7 @@ export default {
|
|||||||
sex:'用户性别',
|
sex:'用户性别',
|
||||||
email:'电子邮箱',
|
email:'电子邮箱',
|
||||||
fromClass:'所属部门',
|
fromClass:'所属部门',
|
||||||
|
fromTenant:'所属租户',
|
||||||
userWork:'用户岗位',
|
userWork:'用户岗位',
|
||||||
userWorkPlease: '请选择用户岗位',
|
userWorkPlease: '请选择用户岗位',
|
||||||
userTip:'用户说明',
|
userTip:'用户说明',
|
||||||
@@ -1747,6 +1744,7 @@ export default {
|
|||||||
lock:'锁定',
|
lock:'锁定',
|
||||||
inactive:'未激活',
|
inactive:'未激活',
|
||||||
active:'激活',
|
active:'激活',
|
||||||
|
permissionTip:'若要选择租户角色,需保证起码租户管理中有一个租户',
|
||||||
},
|
},
|
||||||
config: {
|
config: {
|
||||||
configName: "参数名称",
|
configName: "参数名称",
|
||||||
@@ -1771,6 +1769,55 @@ export default {
|
|||||||
refreshCacheTip: "确定要刷新参数配置缓存吗?",
|
refreshCacheTip: "确定要刷新参数配置缓存吗?",
|
||||||
refreshCacheOk: "刷新缓存成功",
|
refreshCacheOk: "刷新缓存成功",
|
||||||
},
|
},
|
||||||
|
loginSource: {
|
||||||
|
uid: "唯一标识",
|
||||||
|
name: "名称",
|
||||||
|
namePlease: '请正确输入认证源名称',
|
||||||
|
icon: "图标",
|
||||||
|
iconPlease: '可填入图片链接或上传图片路径地址',
|
||||||
|
type: "类型",
|
||||||
|
activeFlag: "状态",
|
||||||
|
remark: "备注说明",
|
||||||
|
createTime: "创建时间",
|
||||||
|
updateTime: "更新时间",
|
||||||
|
ldapUrl: "服务器地址",
|
||||||
|
ldapUrlPlease: '请正确输入LDAP 服务器地址',
|
||||||
|
ldapBaseDN: "基础DN",
|
||||||
|
baseDnPlease: '请正确输入LDAP 基础DN',
|
||||||
|
ldapUserFilter: "用户过滤",
|
||||||
|
userFilterPlease: '请正确输入LDAP 用户过滤',
|
||||||
|
ldapBindDN: "绑定DN",
|
||||||
|
ldapBindPassword: "绑定密码",
|
||||||
|
smtpHost: '服务器地址',
|
||||||
|
smtpHostPlease: '请正确输入SMTP 服务器地址',
|
||||||
|
smtpPort: '端口号',
|
||||||
|
smtpPortPlease: '请正确输入SMTP 端口号',
|
||||||
|
oauth2ClientID: '客户端ID',
|
||||||
|
oauth2ClientIDPlease: '请正确输入OAuth2 客户端ID',
|
||||||
|
oauth2ClientSecret: '客户端密钥',
|
||||||
|
oauth2ClientSecretPlease: '请正确输入OAuth2 客户端密钥',
|
||||||
|
oauth2AuthURL: '授权URL',
|
||||||
|
oauth2AuthURLPlease: '请正确输入OAuth2 授权URL',
|
||||||
|
oauth2TokenURL: '令牌URL',
|
||||||
|
oauth2TokenURLPlease: '请正确输入OAuth2 令牌URL',
|
||||||
|
oauth2UserURL: '用户信息URL',
|
||||||
|
oauth2UserURLPlease: '请正确输入OAuth2 用户信息URL',
|
||||||
|
oauth2AccountField: '账号字段',
|
||||||
|
oauth2AccountFieldPlease: '请正确输入OAuth2 账号字段',
|
||||||
|
oauth2Scopes: '作用域',
|
||||||
|
oauth2ScopesPlease: '请正确输入OAuth2 作用域',
|
||||||
|
oauth2RedirectURL: '重定向URL',
|
||||||
|
oauth2RedirectURLPlease: '请正确输入OAuth2 重定向URL',
|
||||||
|
oauth2RedirectURLTip: '请跳转指定路径(omchost/#/login/oauth2), 重定向携带code和state地址参数',
|
||||||
|
uploadFileTip: '确认要上传认证源图标吗?',
|
||||||
|
uploadFileOk: '认证源图标上传成功',
|
||||||
|
uploadFileErr: '认证源图标上传失败',
|
||||||
|
viewInfoErr: "获取认证源信息失败",
|
||||||
|
addInfo: "添加认证源",
|
||||||
|
editInfo: "修改认证源",
|
||||||
|
delTip: "确认删除认证源编号为 【{num}】 的数据项?",
|
||||||
|
delOk: "删除成功",
|
||||||
|
},
|
||||||
setting: {
|
setting: {
|
||||||
charMaxLen: '位字符长度',
|
charMaxLen: '位字符长度',
|
||||||
saveSubmit: '提交保存',
|
saveSubmit: '提交保存',
|
||||||
@@ -1830,6 +1877,10 @@ export default {
|
|||||||
home: '系统首页',
|
home: '系统首页',
|
||||||
homeTip:'确认要提交当前界面为系统界面吗?',
|
homeTip:'确认要提交当前界面为系统界面吗?',
|
||||||
homeSet:'系统首页设置',
|
homeSet:'系统首页设置',
|
||||||
|
backup: '系统备份',
|
||||||
|
backupInstruction: '系统备份将会对当前系统上运行的网元信息记录及配置文件进行备份,可进行系统的恢复操作!',
|
||||||
|
backupExportTip: '确认要导出系统备份吗?',
|
||||||
|
backupImportTip: '确认要导入系统备份吗?',
|
||||||
},
|
},
|
||||||
role:{
|
role:{
|
||||||
allScopeOptions:'全部数据权限',
|
allScopeOptions:'全部数据权限',
|
||||||
@@ -1874,6 +1925,7 @@ export default {
|
|||||||
cancelGive:'取消授权',
|
cancelGive:'取消授权',
|
||||||
cancelSure:'确认取消用户编号为 【{userId}】 的数据项授权?',
|
cancelSure:'确认取消用户编号为 【{userId}】 的数据项授权?',
|
||||||
batchCancel:'批量取消授权',
|
batchCancel:'批量取消授权',
|
||||||
|
selectUser:'分配用户',
|
||||||
},
|
},
|
||||||
dept:{
|
dept:{
|
||||||
classInfo:'部门信息',
|
classInfo:'部门信息',
|
||||||
@@ -1894,6 +1946,37 @@ export default {
|
|||||||
phone:'联系电话',
|
phone:'联系电话',
|
||||||
email:'邮箱',
|
email:'邮箱',
|
||||||
},
|
},
|
||||||
|
tenant:{
|
||||||
|
classInfo:'租户信息',
|
||||||
|
className:'名称',
|
||||||
|
classId:'编号',
|
||||||
|
classSort:'排序',
|
||||||
|
status:'状态',
|
||||||
|
type:'租赁类型',
|
||||||
|
createTime:'创建时间',
|
||||||
|
highClass:'根级',
|
||||||
|
key:'租赁标识',
|
||||||
|
emailTip:'请输入正确的邮箱地址',
|
||||||
|
phoneTip:'请输入正确的手机号码',
|
||||||
|
node:'根节点',
|
||||||
|
delSure:'确认删除租户名为 【{title}】 的数据项?',
|
||||||
|
delTypeSure:'确认删除租赁类型为 【{tenancyAsset}】,租赁标识为【{tenancyKey}】 的数据项?',
|
||||||
|
open:'展',
|
||||||
|
close:'折',
|
||||||
|
addClass:'新增租户',
|
||||||
|
admin:'负责人',
|
||||||
|
phone:'联系电话',
|
||||||
|
email:'邮箱',
|
||||||
|
SDSST:'网络切片',
|
||||||
|
APN:'接入点',
|
||||||
|
IMSI:'SIM卡',
|
||||||
|
treeSelectTip:'请从左侧租户列表中选择租户进行配置',
|
||||||
|
upfTip:'请选择下拉列表UPF的资源唯一标识',
|
||||||
|
imsiTip:'请选择匹配类型和填入SIM卡号段',
|
||||||
|
radioTip:'请从下拉列表选择基站类型和基站ID',
|
||||||
|
defaultTip:'请选择租赁资产类别, 然后填写资产标识',
|
||||||
|
patternTip:'租赁标识不能包含特殊字符',
|
||||||
|
},
|
||||||
post:{
|
post:{
|
||||||
positionInfo:'岗位信息',
|
positionInfo:'岗位信息',
|
||||||
positionId:'岗位编号',
|
positionId:'岗位编号',
|
||||||
|
|||||||
@@ -20,6 +20,7 @@ import {
|
|||||||
import { useRouter } from 'vue-router';
|
import { useRouter } from 'vue-router';
|
||||||
import useLayoutStore from '@/store/modules/layout';
|
import useLayoutStore from '@/store/modules/layout';
|
||||||
import useAppStore from '@/store/modules/app';
|
import useAppStore from '@/store/modules/app';
|
||||||
|
import useUserStore from '@/store/modules/user';
|
||||||
import useRouterStore from '@/store/modules/router';
|
import useRouterStore from '@/store/modules/router';
|
||||||
import useTabsStore from '@/store/modules/tabs';
|
import useTabsStore from '@/store/modules/tabs';
|
||||||
import useI18n from '@/hooks/useI18n';
|
import useI18n from '@/hooks/useI18n';
|
||||||
@@ -27,7 +28,7 @@ import useAlarmStore from '@/store/modules/alarm';
|
|||||||
import { getServerTime } from '@/api';
|
import { getServerTime } from '@/api';
|
||||||
import { MENU_PATH_INLINE } from '@/constants/menu-constants';
|
import { MENU_PATH_INLINE } from '@/constants/menu-constants';
|
||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
import { parseDateToStr, YYYY_MM_DD_HH_MM_SSZ } from '@/utils/date-utils';
|
||||||
import { parseUrlPath } from '@/plugins/file-static-url';
|
import { parseUrlPath } from '@/plugins/file-static-url';
|
||||||
const { proConfig, waterMarkContent } = useLayoutStore();
|
const { proConfig, waterMarkContent } = useLayoutStore();
|
||||||
const { t, currentLocale } = useI18n();
|
const { t, currentLocale } = useI18n();
|
||||||
@@ -64,19 +65,28 @@ watch(
|
|||||||
{ immediate: true }
|
{ immediate: true }
|
||||||
);
|
);
|
||||||
|
|
||||||
// 动态路由添加到菜单面板
|
const menuData = computed(() => {
|
||||||
const rootRoute = router.getRoutes().find(r => r.name === 'Root');
|
// 动态路由添加到菜单面板
|
||||||
if (rootRoute) {
|
const rootRoute = router.getRoutes().find(r => r.name === 'Root');
|
||||||
const children = routerStore.setRootRouterData(rootRoute.children);
|
if (rootRoute) {
|
||||||
const buildRouterData = routerStore.buildRouterData;
|
const children = routerStore.setRootRouterData(rootRoute.children);
|
||||||
if (buildRouterData.length > 0) {
|
const buildRouterData = routerStore.buildRouterData;
|
||||||
rootRoute.children = children.concat(buildRouterData);
|
if (buildRouterData.length > 0) {
|
||||||
} else {
|
rootRoute.children = children.concat(buildRouterData);
|
||||||
rootRoute.children = children;
|
} else {
|
||||||
|
rootRoute.children = children;
|
||||||
|
}
|
||||||
|
// console.log(JSON.parse(JSON.stringify(rootRoute.children)));
|
||||||
|
if (!useUserStore().roles.includes('tenant')) {
|
||||||
|
rootRoute.children = rootRoute.children.filter(
|
||||||
|
item => item.name !== 'Index'
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
const { menuData } = getMenuData(clearMenuItem(router.getRoutes()));
|
const { menuData } = getMenuData(clearMenuItem(router.getRoutes()));
|
||||||
|
return menuData;
|
||||||
|
});
|
||||||
|
|
||||||
/**面包屑数据对象,排除根节点和首页不显示 */
|
/**面包屑数据对象,排除根节点和首页不显示 */
|
||||||
const breadcrumb = computed(() => {
|
const breadcrumb = computed(() => {
|
||||||
@@ -198,6 +208,7 @@ let serverTime = reactive({
|
|||||||
zone: 'UTC', // 时区 UTC
|
zone: 'UTC', // 时区 UTC
|
||||||
interval: null as any, // 定时器
|
interval: null as any, // 定时器
|
||||||
});
|
});
|
||||||
|
let activeAlarmRefresh = 0;
|
||||||
|
|
||||||
// 获取服务器时间
|
// 获取服务器时间
|
||||||
function fnGetServerTime() {
|
function fnGetServerTime() {
|
||||||
@@ -211,10 +222,18 @@ function fnGetServerTime() {
|
|||||||
serverTime.timestamp = parseInt(res.data.timestamp);
|
serverTime.timestamp = parseInt(res.data.timestamp);
|
||||||
serverTime.interval = setInterval(() => {
|
serverTime.interval = setInterval(() => {
|
||||||
serverTime.timestamp += 1000;
|
serverTime.timestamp += 1000;
|
||||||
|
activeAlarmRefresh += 1;
|
||||||
// serverTimeStr.value = parseDateToStr(serverTime.timestamp);
|
// serverTimeStr.value = parseDateToStr(serverTime.timestamp);
|
||||||
// 用DOM直接修改
|
// 用DOM直接修改
|
||||||
if (serverTimeDom) {
|
if (serverTimeDom) {
|
||||||
serverTimeDom.innerText = parseDateToStr(serverTime.timestamp);
|
serverTimeDom.innerText = parseDateToStr(
|
||||||
|
serverTime.timestamp,
|
||||||
|
YYYY_MM_DD_HH_MM_SSZ
|
||||||
|
);
|
||||||
|
}
|
||||||
|
if (activeAlarmRefresh === 5) {
|
||||||
|
useAlarmStore().fnGetActiveAlarmInfo();
|
||||||
|
activeAlarmRefresh = 0;
|
||||||
}
|
}
|
||||||
}, 1000);
|
}, 1000);
|
||||||
}
|
}
|
||||||
@@ -255,6 +274,7 @@ onUnmounted(() => {
|
|||||||
v-bind="proConfig"
|
v-bind="proConfig"
|
||||||
:iconfont-url="scriptUrl"
|
:iconfont-url="scriptUrl"
|
||||||
:locale="fnLocale"
|
:locale="fnLocale"
|
||||||
|
:sider-width="256"
|
||||||
>
|
>
|
||||||
<!--插槽-菜单头-->
|
<!--插槽-菜单头-->
|
||||||
<template #menuHeaderRender>
|
<template #menuHeaderRender>
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import svgDark from '@/assets/svg/dark.svg';
|
|||||||
import { MenuInfo } from 'ant-design-vue/es/menu/src/interface';
|
import { MenuInfo } from 'ant-design-vue/es/menu/src/interface';
|
||||||
import { viewTransitionTheme } from 'antdv-pro-layout';
|
import { viewTransitionTheme } from 'antdv-pro-layout';
|
||||||
import { ProModal } from 'antdv-pro-modal';
|
import { ProModal } from 'antdv-pro-modal';
|
||||||
|
import SearchMenu from './SearchMenu.vue';
|
||||||
import { ref } from 'vue';
|
import { ref } from 'vue';
|
||||||
import { useRoute, useRouter } from 'vue-router';
|
import { useRoute, useRouter } from 'vue-router';
|
||||||
import { useFullscreen } from '@vueuse/core';
|
import { useFullscreen } from '@vueuse/core';
|
||||||
@@ -14,6 +15,9 @@ import useAppStore from '@/store/modules/app';
|
|||||||
import useUserStore from '@/store/modules/user';
|
import useUserStore from '@/store/modules/user';
|
||||||
import useAlarmStore from '@/store/modules/alarm';
|
import useAlarmStore from '@/store/modules/alarm';
|
||||||
import useMaskStore from '@/store/modules/mask';
|
import useMaskStore from '@/store/modules/mask';
|
||||||
|
import { dbClear } from '@/utils/cache-db-utils';
|
||||||
|
import { CACHE_DB_TABLE_DND } from '@/constants/cache-keys-constants';
|
||||||
|
import { TENANTADMIN_ROLE_KEY } from '@/constants/admin-constants';
|
||||||
const { isFullscreen, toggle } = useFullscreen();
|
const { isFullscreen, toggle } = useFullscreen();
|
||||||
const { t, changeLocale, optionsLocale } = useI18n();
|
const { t, changeLocale, optionsLocale } = useI18n();
|
||||||
const layoutStore = useLayoutStore();
|
const layoutStore = useLayoutStore();
|
||||||
@@ -33,7 +37,10 @@ function fnClick({ key }: MenuInfo) {
|
|||||||
router.push({ name: 'Profile' });
|
router.push({ name: 'Profile' });
|
||||||
break;
|
break;
|
||||||
case 'logout':
|
case 'logout':
|
||||||
userStore.fnLogOut().finally(() => router.push({ name: 'Login' }));
|
userStore.fnLogOut().finally(() => {
|
||||||
|
dbClear(CACHE_DB_TABLE_DND);
|
||||||
|
router.push({ name: 'Login' });
|
||||||
|
});
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -78,21 +85,33 @@ function fnChangeLocale(e: any) {
|
|||||||
|
|
||||||
<template>
|
<template>
|
||||||
<a-space :size="12" align="center">
|
<a-space :size="12" align="center">
|
||||||
<a-tooltip placement="bottomRight">
|
<!-- 搜索功能 -->
|
||||||
<template #title>{{ t('loayouts.rightContent.alarm') }}</template>
|
<span >
|
||||||
<a-button type="text" style="color: inherit" @click="fnClickAlarm">
|
<SearchMenu />
|
||||||
<template #icon>
|
</span>
|
||||||
<a-badge
|
|
||||||
:count="useAlarmStore().activeAlarmTotal"
|
<span v-roles:has="[TENANTADMIN_ROLE_KEY]">
|
||||||
:overflow-count="99"
|
<a-tooltip placement="bottom">
|
||||||
status="warning"
|
<template #title>{{ t('loayouts.rightContent.alarm') }}</template>
|
||||||
style="color: inherit"
|
<a-button
|
||||||
>
|
type="text"
|
||||||
<BellOutlined />
|
style="color: inherit"
|
||||||
</a-badge>
|
@click="fnClickAlarm"
|
||||||
</template>
|
v-perms:has="['faultManage:active-alarm:index']"
|
||||||
</a-button>
|
>
|
||||||
</a-tooltip>
|
<template #icon>
|
||||||
|
<a-badge
|
||||||
|
:count="useAlarmStore().activeAlarmTotal"
|
||||||
|
:overflow-count="99"
|
||||||
|
status="warning"
|
||||||
|
style="color: inherit"
|
||||||
|
>
|
||||||
|
<BellOutlined />
|
||||||
|
</a-badge>
|
||||||
|
</template>
|
||||||
|
</a-button>
|
||||||
|
</a-tooltip>
|
||||||
|
</span>
|
||||||
|
|
||||||
<!-- 锁屏操作 -->
|
<!-- 锁屏操作 -->
|
||||||
<span v-perms:has="['system:setting:lock']">
|
<span v-perms:has="['system:setting:lock']">
|
||||||
|
|||||||
@@ -0,0 +1,380 @@
|
|||||||
|
<template>
|
||||||
|
<!-- 搜索按钮 -->
|
||||||
|
<a-tooltip placement="bottom">
|
||||||
|
<template #title>{{ t('common.search') }}</template>
|
||||||
|
<a-button type="text" style="color: inherit" @click="fnClickSearch">
|
||||||
|
<template #icon>
|
||||||
|
<SearchOutlined />
|
||||||
|
</template>
|
||||||
|
</a-button>
|
||||||
|
</a-tooltip>
|
||||||
|
|
||||||
|
<!-- 搜索弹窗 -->
|
||||||
|
<ProModal
|
||||||
|
:drag="false"
|
||||||
|
:center-y="true"
|
||||||
|
:width="600"
|
||||||
|
:minHeight="400"
|
||||||
|
:mask-closable="true"
|
||||||
|
v-model:open="searchModalOpen"
|
||||||
|
:title="t('common.search')"
|
||||||
|
:footer="null"
|
||||||
|
@cancel="fnCloseSearch"
|
||||||
|
>
|
||||||
|
<div class="search-modal-content">
|
||||||
|
<a-input
|
||||||
|
ref="searchInputRef"
|
||||||
|
v-model:value="searchKeyword"
|
||||||
|
:placeholder="t('common.searchPlease')"
|
||||||
|
size="large"
|
||||||
|
style="margin-bottom: 16px"
|
||||||
|
@keydown="fnHandleKeydown"
|
||||||
|
>
|
||||||
|
<template #prefix>
|
||||||
|
<SearchOutlined style="color: #bfbfbf" />
|
||||||
|
</template>
|
||||||
|
</a-input>
|
||||||
|
|
||||||
|
<div class="search-results">
|
||||||
|
<div v-if="filteredMenus.length === 0" class="no-results">
|
||||||
|
<a-empty
|
||||||
|
:description="
|
||||||
|
searchKeyword ? t('common.noData') : t('common.searchTip')
|
||||||
|
"
|
||||||
|
:image="false"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<div v-else class="menu-list">
|
||||||
|
<div
|
||||||
|
v-for="menu in filteredMenus"
|
||||||
|
:key="menu.key"
|
||||||
|
class="menu-item"
|
||||||
|
@click="fnSelectMenu(menu)"
|
||||||
|
>
|
||||||
|
<div class="menu-icon">
|
||||||
|
<!-- 处理自定义图标字体 -->
|
||||||
|
<IconFont
|
||||||
|
v-if="menu.icon && menu.icon.startsWith('icon-')"
|
||||||
|
:type="menu.icon"
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
<!-- 处理Ant Design图标组件 -->
|
||||||
|
<component
|
||||||
|
:is="menu.icon"
|
||||||
|
v-else-if="menu.icon && !menu.icon.startsWith('icon-')"
|
||||||
|
class="icon"
|
||||||
|
/>
|
||||||
|
<!-- 默认图标 -->
|
||||||
|
<FolderOutlined v-else class="icon" />
|
||||||
|
</div>
|
||||||
|
<div class="menu-info">
|
||||||
|
<div class="menu-title">{{ menu.title }}</div>
|
||||||
|
</div>
|
||||||
|
<div class="menu-action">
|
||||||
|
<RightOutlined />
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</ProModal>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
import { getMenuData, clearMenuItem } from 'antdv-pro-layout';
|
||||||
|
import { ProModal } from 'antdv-pro-modal';
|
||||||
|
import IconFont from '@/components/IconFont/index.vue';
|
||||||
|
import { ref, computed, nextTick } from 'vue';
|
||||||
|
import { useRouter } from 'vue-router';
|
||||||
|
import useI18n from '@/hooks/useI18n';
|
||||||
|
import useUserStore from '@/store/modules/user';
|
||||||
|
import useRouterStore from '@/store/modules/router';
|
||||||
|
|
||||||
|
const { t } = useI18n();
|
||||||
|
const userStore = useUserStore();
|
||||||
|
const routerStore = useRouterStore();
|
||||||
|
const router = useRouter();
|
||||||
|
|
||||||
|
// 搜索相关状态
|
||||||
|
const searchModalOpen = ref<boolean>(false);
|
||||||
|
const searchKeyword = ref<string>('');
|
||||||
|
const searchInputRef = ref();
|
||||||
|
|
||||||
|
// 获取所有可搜索的菜单项
|
||||||
|
const searchableMenus = computed(() => {
|
||||||
|
const menus: Array<{
|
||||||
|
title: string;
|
||||||
|
path: string;
|
||||||
|
icon?: string;
|
||||||
|
key: string;
|
||||||
|
routeName?: string;
|
||||||
|
}> = [];
|
||||||
|
|
||||||
|
// 使用和BasicLayout完全相同的菜单数据获取逻辑
|
||||||
|
const getMenuDataForSearch = () => {
|
||||||
|
// 动态路由添加到菜单面板
|
||||||
|
const rootRoute = router.getRoutes().find(r => r.name === 'Root');
|
||||||
|
if (rootRoute) {
|
||||||
|
const children = routerStore.setRootRouterData(rootRoute.children);
|
||||||
|
const buildRouterData = routerStore.buildRouterData;
|
||||||
|
if (buildRouterData.length > 0) {
|
||||||
|
rootRoute.children = children.concat(buildRouterData);
|
||||||
|
} else {
|
||||||
|
rootRoute.children = children;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 根据用户角色过滤
|
||||||
|
if (!userStore.roles.includes('tenant')) {
|
||||||
|
rootRoute.children = rootRoute.children.filter(
|
||||||
|
item => item.name !== 'Index'
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 使用和BasicLayout相同的处理方法
|
||||||
|
const { menuData } = getMenuData(clearMenuItem(router.getRoutes()));
|
||||||
|
return menuData;
|
||||||
|
};
|
||||||
|
|
||||||
|
// 递归获取所有路由项
|
||||||
|
const getRouteItems = (routes: any[], parentPath = '') => {
|
||||||
|
routes.forEach((route: any) => {
|
||||||
|
// 跳过根路径和不显示的菜单
|
||||||
|
if (route.path === '/' || route.path === '' || route.meta?.hideInMenu) {
|
||||||
|
// 继续处理子路由
|
||||||
|
if (route.children && route.children.length > 0) {
|
||||||
|
getRouteItems(route.children, route.path === '/' ? '' : route.path);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 构建完整路径
|
||||||
|
let fullPath = route.path;
|
||||||
|
if (!route.path.startsWith('/') && parentPath) {
|
||||||
|
fullPath = `${parentPath}/${route.path}`;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 只添加有meta.title的路由项
|
||||||
|
if (route.meta && route.meta.title) {
|
||||||
|
try {
|
||||||
|
const title = t(route.meta.title);
|
||||||
|
// 避免重复添加已存在的路由
|
||||||
|
const exists = menus.find(
|
||||||
|
m => m.routeName === route.name || m.path === fullPath
|
||||||
|
);
|
||||||
|
if (!exists) {
|
||||||
|
menus.push({
|
||||||
|
title: title,
|
||||||
|
path: fullPath,
|
||||||
|
icon: route.meta.icon,
|
||||||
|
key: route.name || fullPath,
|
||||||
|
routeName: route.name,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
// 如果翻译失败,使用原始标题
|
||||||
|
const exists = menus.find(
|
||||||
|
m => m.routeName === route.name || m.path === fullPath
|
||||||
|
);
|
||||||
|
if (!exists) {
|
||||||
|
menus.push({
|
||||||
|
title: route.meta.title,
|
||||||
|
path: fullPath,
|
||||||
|
icon: route.meta.icon,
|
||||||
|
key: route.name || fullPath,
|
||||||
|
routeName: route.name,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 处理子路由
|
||||||
|
if (route.children && route.children.length > 0) {
|
||||||
|
getRouteItems(route.children, fullPath);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
|
// 使用和菜单面板相同的数据源
|
||||||
|
const menuRoutes = getMenuDataForSearch();
|
||||||
|
|
||||||
|
if (menuRoutes && menuRoutes.length > 0) {
|
||||||
|
getRouteItems(menuRoutes);
|
||||||
|
}
|
||||||
|
|
||||||
|
return menus;
|
||||||
|
});
|
||||||
|
|
||||||
|
// 过滤的菜单项
|
||||||
|
const filteredMenus = computed(() => {
|
||||||
|
if (!searchKeyword.value.trim()) {
|
||||||
|
return searchableMenus.value.slice(0, 10); // 默认显示前10个
|
||||||
|
}
|
||||||
|
|
||||||
|
// return searchableMenus.value.filter(menu =>
|
||||||
|
// menu.title.toLowerCase().includes(searchKeyword.value.toLowerCase()) ||
|
||||||
|
// menu.path.toLowerCase().includes(searchKeyword.value.toLowerCase())
|
||||||
|
// ).slice(0, 10);
|
||||||
|
const value = searchKeyword.value.toLowerCase();
|
||||||
|
return searchableMenus.value
|
||||||
|
.filter(menu => menu.title.toLowerCase().includes(value))
|
||||||
|
.slice(0, 10);
|
||||||
|
});
|
||||||
|
|
||||||
|
/**打开搜索弹窗 */
|
||||||
|
function fnClickSearch() {
|
||||||
|
searchModalOpen.value = true;
|
||||||
|
searchKeyword.value = '';
|
||||||
|
|
||||||
|
nextTick(() => {
|
||||||
|
searchInputRef.value?.focus();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**关闭搜索弹窗 */
|
||||||
|
function fnCloseSearch() {
|
||||||
|
searchModalOpen.value = false;
|
||||||
|
searchKeyword.value = '';
|
||||||
|
}
|
||||||
|
|
||||||
|
/**选择菜单项并跳转 */
|
||||||
|
function fnSelectMenu(menu: any) {
|
||||||
|
try {
|
||||||
|
// 优先使用路由名称跳转
|
||||||
|
if (menu.routeName) {
|
||||||
|
router.push({ name: menu.routeName });
|
||||||
|
} else {
|
||||||
|
router.push(menu.path);
|
||||||
|
}
|
||||||
|
fnCloseSearch();
|
||||||
|
} catch (error) {
|
||||||
|
// 如果跳转失败,尝试直接使用路径
|
||||||
|
try {
|
||||||
|
router.push(menu.path);
|
||||||
|
fnCloseSearch();
|
||||||
|
} catch (secondError) {
|
||||||
|
// 可以在这里添加错误提示
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**键盘事件处理 */
|
||||||
|
function fnHandleKeydown(e: KeyboardEvent) {
|
||||||
|
if (e.key === 'Escape') {
|
||||||
|
fnCloseSearch();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style lang="less" scoped>
|
||||||
|
.search-modal-content {
|
||||||
|
.search-results {
|
||||||
|
max-height: 400px;
|
||||||
|
overflow-y: auto;
|
||||||
|
|
||||||
|
.no-results {
|
||||||
|
text-align: center;
|
||||||
|
padding: 40px 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-list {
|
||||||
|
.menu-item {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
padding: 12px 16px;
|
||||||
|
border-radius: 8px;
|
||||||
|
cursor: pointer;
|
||||||
|
transition: all 0.2s ease;
|
||||||
|
margin-bottom: 4px;
|
||||||
|
|
||||||
|
&:hover {
|
||||||
|
background-color: #f5f5f5;
|
||||||
|
|
||||||
|
.menu-action {
|
||||||
|
opacity: 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-icon {
|
||||||
|
margin-right: 12px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
width: 32px;
|
||||||
|
height: 32px;
|
||||||
|
background-color: #f0f2f5;
|
||||||
|
border-radius: 6px;
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
font-size: 16px;
|
||||||
|
color: #666;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-info {
|
||||||
|
flex: 1;
|
||||||
|
min-width: 0;
|
||||||
|
|
||||||
|
.menu-title {
|
||||||
|
font-size: 14px;
|
||||||
|
font-weight: 500;
|
||||||
|
color: #262626;
|
||||||
|
margin-bottom: 2px;
|
||||||
|
overflow: hidden;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-path {
|
||||||
|
font-size: 12px;
|
||||||
|
color: #8c8c8c;
|
||||||
|
overflow: hidden;
|
||||||
|
text-overflow: ellipsis;
|
||||||
|
white-space: nowrap;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-action {
|
||||||
|
opacity: 0;
|
||||||
|
transition: opacity 0.2s ease;
|
||||||
|
color: #bfbfbf;
|
||||||
|
font-size: 12px;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// 暗黑主题支持
|
||||||
|
[data-theme='dark'] {
|
||||||
|
.search-modal-content {
|
||||||
|
.search-results {
|
||||||
|
.menu-list {
|
||||||
|
.menu-item {
|
||||||
|
&:hover {
|
||||||
|
background-color: #303030;
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-icon {
|
||||||
|
background-color: #262626;
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
color: #bfbfbf;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-info {
|
||||||
|
.menu-title {
|
||||||
|
color: #f0f0f0;
|
||||||
|
}
|
||||||
|
|
||||||
|
.menu-path {
|
||||||
|
color: #8c8c8c;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -61,7 +61,7 @@ type OptionsType = {
|
|||||||
/**请求地址 */
|
/**请求地址 */
|
||||||
url: string;
|
url: string;
|
||||||
/**请求方法 */
|
/**请求方法 */
|
||||||
method: 'get' | 'post' | 'put' | 'delete' | 'PATCH';
|
method: 'get' | 'post' | 'put' | 'delete' | 'PATCH' | 'GET' | 'POST' | 'PUT' | 'DELETE';
|
||||||
/**请求头 */
|
/**请求头 */
|
||||||
headers?: HeadersInit;
|
headers?: HeadersInit;
|
||||||
/**地址栏参数 */
|
/**地址栏参数 */
|
||||||
@@ -198,7 +198,7 @@ function beforeRequest(options: OptionsType): OptionsType | Promise<any> {
|
|||||||
if (options.method === 'get') return options;
|
if (options.method === 'get') return options;
|
||||||
|
|
||||||
// 非get参数提交
|
// 非get参数提交
|
||||||
let body = options.data
|
let body = options.data;
|
||||||
if (body instanceof FormData) {
|
if (body instanceof FormData) {
|
||||||
options.body = body;
|
options.body = body;
|
||||||
} else if (body) {
|
} else if (body) {
|
||||||
|
|||||||
@@ -119,17 +119,15 @@ export class WS {
|
|||||||
};
|
};
|
||||||
// 用于指定当从服务器接受到信息时的回调函数。
|
// 用于指定当从服务器接受到信息时的回调函数。
|
||||||
ws.onmessage = ev => {
|
ws.onmessage = ev => {
|
||||||
|
if (ev.type !== 'message') return;
|
||||||
// 解析文本消息
|
// 解析文本消息
|
||||||
if (ev.type === 'message') {
|
try {
|
||||||
const data = ev.data;
|
const jsonData = JSON.parse(ev.data);
|
||||||
try {
|
if (typeof options.onmessage === 'function') {
|
||||||
const jsonData = JSON.parse(data);
|
options.onmessage(jsonData);
|
||||||
if (typeof options.onmessage === 'function') {
|
|
||||||
options.onmessage(jsonData);
|
|
||||||
}
|
|
||||||
} catch (error) {
|
|
||||||
console.error('websocket message formatting error', error);
|
|
||||||
}
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error('websocket message formatting error', error);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
// 用于指定连接关闭后的回调函数。
|
// 用于指定连接关闭后的回调函数。
|
||||||
@@ -221,7 +219,7 @@ export class WS {
|
|||||||
this.heartInterval = window.setInterval(() => {
|
this.heartInterval = window.setInterval(() => {
|
||||||
this.send({
|
this.send({
|
||||||
requestId: `${Date.now()}`,
|
requestId: `${Date.now()}`,
|
||||||
type: 'ping',
|
type: 'PING',
|
||||||
});
|
});
|
||||||
}, heartTimer);
|
}, heartTimer);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -13,6 +13,8 @@ import { validHttp } from '@/utils/regular-utils';
|
|||||||
import useUserStore from '@/store/modules/user';
|
import useUserStore from '@/store/modules/user';
|
||||||
import useAppStore from '@/store/modules/app';
|
import useAppStore from '@/store/modules/app';
|
||||||
import useRouterStore from '@/store/modules/router';
|
import useRouterStore from '@/store/modules/router';
|
||||||
|
import useNeInfoStore from '@/store/modules/neinfo';
|
||||||
|
import useNeListStore from '@/store/modules/ne_list';
|
||||||
|
|
||||||
// NProgress Configuration
|
// NProgress Configuration
|
||||||
NProgress.configure({ showSpinner: false });
|
NProgress.configure({ showSpinner: false });
|
||||||
@@ -30,12 +32,15 @@ const constantRoutes: RouteRecordRaw[] = [
|
|||||||
name: 'Root',
|
name: 'Root',
|
||||||
component: BasicLayout,
|
component: BasicLayout,
|
||||||
redirect: '/index',
|
redirect: '/index',
|
||||||
|
// redirect: '/monitor/dashboard',
|
||||||
children: [
|
children: [
|
||||||
{
|
{
|
||||||
path: '/index',
|
path: '/index',
|
||||||
name: 'Index',
|
name: 'Index',
|
||||||
meta: { title: 'router.index', icon: 'icon-pcduan' },
|
meta: { title: 'router.index', icon: 'icon-pcduan' },
|
||||||
component: () => import('@/views/index.vue'),
|
component: () => import('@/views/index.vue'),
|
||||||
|
// meta: { title: 'router.index', icon: 'icon-pcduan', hideInMenu: true },
|
||||||
|
// redirect: '/monitor/dashboard',
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: '/account',
|
path: '/account',
|
||||||
@@ -63,11 +68,16 @@ const constantRoutes: RouteRecordRaw[] = [
|
|||||||
},
|
},
|
||||||
],
|
],
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
path: '/login/oauth2',
|
||||||
|
name: 'LoginOAuth2', // 第三方认证重定向
|
||||||
|
component: () => import('@/views/login/oauth2.vue'),
|
||||||
|
},
|
||||||
{
|
{
|
||||||
path: '/login',
|
path: '/login',
|
||||||
name: 'Login',
|
name: 'Login',
|
||||||
meta: { title: 'router.login' },
|
meta: { title: 'router.login' },
|
||||||
component: () => import('@/views/login.vue'),
|
component: () => import('@/views/login/index.vue'),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
path: '/register',
|
path: '/register',
|
||||||
@@ -156,7 +166,7 @@ router.afterEach((to, from, failure) => {
|
|||||||
/**无Token可访问页面地址白名单 */
|
/**无Token可访问页面地址白名单 */
|
||||||
const WHITE_LIST: string[] = [
|
const WHITE_LIST: string[] = [
|
||||||
'/login',
|
'/login',
|
||||||
'/auth-redirect',
|
'/login/oauth2',
|
||||||
'/help',
|
'/help',
|
||||||
'/register',
|
'/register',
|
||||||
'/quick-start',
|
'/quick-start',
|
||||||
@@ -182,7 +192,12 @@ router.beforeEach(async (to, from, next) => {
|
|||||||
next({ name: 'Index' });
|
next({ name: 'Index' });
|
||||||
}
|
}
|
||||||
|
|
||||||
const token = getToken();
|
let token = getToken();
|
||||||
|
|
||||||
|
// 免用户登录认证
|
||||||
|
if (!appStore.loginAuth) {
|
||||||
|
token = '== Not Login Auth ==';
|
||||||
|
}
|
||||||
|
|
||||||
// 没有token
|
// 没有token
|
||||||
if (!token) {
|
if (!token) {
|
||||||
@@ -205,6 +220,9 @@ router.beforeEach(async (to, from, next) => {
|
|||||||
const user = useUserStore();
|
const user = useUserStore();
|
||||||
if (user.roles && user.roles.length === 0) {
|
if (user.roles && user.roles.length === 0) {
|
||||||
try {
|
try {
|
||||||
|
useNeInfoStore().fnRefreshNelist();
|
||||||
|
useNeListStore().fnNelistRefresh();
|
||||||
|
|
||||||
// 获取用户信息
|
// 获取用户信息
|
||||||
await user.fnGetInfo();
|
await user.fnGetInfo();
|
||||||
// 获取路由信息
|
// 获取路由信息
|
||||||
|
|||||||
@@ -1,9 +1,10 @@
|
|||||||
import { getSysConf } from '@/api';
|
import { getSysConf } from '@/api';
|
||||||
import { CACHE_LOCAL_I18N } from '@/constants/cache-keys-constants';
|
import { CACHE_LOCAL_I18N, CACHE_SESSION_CRYPTO_API } from '@/constants/cache-keys-constants';
|
||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { removeToken } from '@/plugins/auth-token';
|
import { removeToken } from '@/plugins/auth-token';
|
||||||
import { parseUrlPath } from '@/plugins/file-static-url';
|
import { parseUrlPath } from '@/plugins/file-static-url';
|
||||||
import { localGet, localSet } from '@/utils/cache-local-utils';
|
import { localGet, localSet } from '@/utils/cache-local-utils';
|
||||||
|
import { sessionSet } from '@/utils/cache-session-utils';
|
||||||
import { defineStore } from 'pinia';
|
import { defineStore } from 'pinia';
|
||||||
|
|
||||||
/**应用参数类型 */
|
/**应用参数类型 */
|
||||||
@@ -20,6 +21,10 @@ type AppStore = {
|
|||||||
buildTime: string;
|
buildTime: string;
|
||||||
/**系统引导使用 */
|
/**系统引导使用 */
|
||||||
bootloader: boolean;
|
bootloader: boolean;
|
||||||
|
// 用户登录认证
|
||||||
|
loginAuth: boolean;
|
||||||
|
// 用户接口加密
|
||||||
|
cryptoApi: boolean;
|
||||||
// 序列号
|
// 序列号
|
||||||
serialNum: string;
|
serialNum: string;
|
||||||
/**应用版权声明 */
|
/**应用版权声明 */
|
||||||
@@ -52,6 +57,8 @@ const useAppStore = defineStore('app', {
|
|||||||
version: `-`,
|
version: `-`,
|
||||||
buildTime: `-`,
|
buildTime: `-`,
|
||||||
bootloader: false,
|
bootloader: false,
|
||||||
|
loginAuth: true,
|
||||||
|
cryptoApi: true,
|
||||||
serialNum: `-`,
|
serialNum: `-`,
|
||||||
copyright: `Copyright ©2023 For ${import.meta.env.VITE_APP_NAME}`,
|
copyright: `Copyright ©2023 For ${import.meta.env.VITE_APP_NAME}`,
|
||||||
logoType: 'icon',
|
logoType: 'icon',
|
||||||
@@ -85,6 +92,9 @@ const useAppStore = defineStore('app', {
|
|||||||
if (this.bootloader) {
|
if (this.bootloader) {
|
||||||
removeToken();
|
removeToken();
|
||||||
}
|
}
|
||||||
|
this.loginAuth = res.data.loginAuth !== 'false';
|
||||||
|
this.cryptoApi = res.data.cryptoApi !== 'false';
|
||||||
|
sessionSet(CACHE_SESSION_CRYPTO_API, res.data.cryptoApi);
|
||||||
this.serialNum = res.data.serialNum;
|
this.serialNum = res.data.serialNum;
|
||||||
this.appName = res.data.title;
|
this.appName = res.data.title;
|
||||||
this.copyright = res.data.copyright;
|
this.copyright = res.data.copyright;
|
||||||
|
|||||||
@@ -20,7 +20,7 @@ type MaskStateType = {
|
|||||||
const useMaskStore = defineStore('mask', {
|
const useMaskStore = defineStore('mask', {
|
||||||
state: (): MaskStateType => ({
|
state: (): MaskStateType => ({
|
||||||
type: (localGet(CACHE_LOCAL_MASK) || 'none') as MaskStateType['type'],
|
type: (localGet(CACHE_LOCAL_MASK) || 'none') as MaskStateType['type'],
|
||||||
lockPasswd: localGet(CACHE_LOCAL_LOCK_PASSWD) || '',
|
lockPasswd: atob(localGet(CACHE_LOCAL_LOCK_PASSWD) || ''),
|
||||||
lockTimeout: 0,
|
lockTimeout: 0,
|
||||||
}),
|
}),
|
||||||
getters: {},
|
getters: {},
|
||||||
@@ -59,7 +59,7 @@ const useMaskStore = defineStore('mask', {
|
|||||||
}, 5_000);
|
}, 5_000);
|
||||||
}
|
}
|
||||||
if (type === 'lock') {
|
if (type === 'lock') {
|
||||||
localSet(CACHE_LOCAL_LOCK_PASSWD, this.lockPasswd);
|
localSet(CACHE_LOCAL_LOCK_PASSWD, btoa(this.lockPasswd));
|
||||||
} else {
|
} else {
|
||||||
localRemove(CACHE_LOCAL_LOCK_PASSWD);
|
localRemove(CACHE_LOCAL_LOCK_PASSWD);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,123 @@
|
|||||||
|
import { defineStore } from 'pinia';
|
||||||
|
import {
|
||||||
|
RESULT_CODE_SUCCESS,
|
||||||
|
RESULT_MSG_SUCCESS,
|
||||||
|
} from '@/constants/result-constants';
|
||||||
|
import { listAllNeInfo } from '@/api/ne/neInfo';
|
||||||
|
import { parseDataToOptions } from '@/utils/parse-tree-utils';
|
||||||
|
|
||||||
|
/**网元列表信息类型 */
|
||||||
|
type NeList = {
|
||||||
|
/**网元列表 */
|
||||||
|
neList: Record<string, any>[];
|
||||||
|
/**级联options树结构 */
|
||||||
|
neCascaderOptions: Record<string, any>[];
|
||||||
|
/**选择器单级父类型 */
|
||||||
|
neSelectOtions: Record<string, any>[];
|
||||||
|
};
|
||||||
|
|
||||||
|
const useNeListStore = defineStore('ne_list', {
|
||||||
|
state: (): NeList => ({
|
||||||
|
neList: [],
|
||||||
|
neCascaderOptions: [],
|
||||||
|
neSelectOtions: [],
|
||||||
|
}),
|
||||||
|
getters: {
|
||||||
|
/**
|
||||||
|
* 网元列表
|
||||||
|
* @param state 内部属性不用传入
|
||||||
|
* @returns 级联options
|
||||||
|
*/
|
||||||
|
getNeList(state) {
|
||||||
|
return state.neList;
|
||||||
|
},
|
||||||
|
/**
|
||||||
|
* 获取级联options树结构
|
||||||
|
* @param state 内部属性不用传入
|
||||||
|
* @returns 级联options
|
||||||
|
*/
|
||||||
|
getNeCascaderOptions(state) {
|
||||||
|
return state.neCascaderOptions;
|
||||||
|
},
|
||||||
|
/**
|
||||||
|
* 选择器单级父类型
|
||||||
|
* @param state 内部属性不用传入
|
||||||
|
* @returns 选择options
|
||||||
|
*/
|
||||||
|
getNeSelectOtions(state) {
|
||||||
|
return state.neSelectOtions;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
actions: {
|
||||||
|
// 刷新网元列表
|
||||||
|
async fnNelistRefresh() {
|
||||||
|
this.neList = [];
|
||||||
|
return await this.fnNelist();
|
||||||
|
},
|
||||||
|
// 获取网元列表
|
||||||
|
async fnNelist() {
|
||||||
|
// 有数据不请求
|
||||||
|
if (this.neList.length > 0) {
|
||||||
|
return {
|
||||||
|
code: RESULT_CODE_SUCCESS,
|
||||||
|
msg: RESULT_MSG_SUCCESS['en_US'],
|
||||||
|
data: this.neList,
|
||||||
|
};
|
||||||
|
}
|
||||||
|
const res = await listAllNeInfo({
|
||||||
|
bandStatus: false,
|
||||||
|
bandHost: false,
|
||||||
|
});
|
||||||
|
if (res.code === RESULT_CODE_SUCCESS) {
|
||||||
|
// 原始列表
|
||||||
|
this.neList = JSON.parse(JSON.stringify(res.data));
|
||||||
|
|
||||||
|
// 转级联数据
|
||||||
|
const options = parseDataToOptions(
|
||||||
|
res.data,
|
||||||
|
'neType',
|
||||||
|
'neName',
|
||||||
|
'neId'
|
||||||
|
);
|
||||||
|
this.neCascaderOptions = options;
|
||||||
|
|
||||||
|
// 转选择器单级父类型
|
||||||
|
this.neSelectOtions = options.map(item => {
|
||||||
|
return {
|
||||||
|
label: item.label,
|
||||||
|
value: item.value,
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
|
return res;
|
||||||
|
},
|
||||||
|
/**
|
||||||
|
* 含有网元
|
||||||
|
* @param metaNeType ['udm', 'ims', 'udm+ims', 'SGWC'] 支持大小写
|
||||||
|
* @returns boolean
|
||||||
|
*/
|
||||||
|
fnHasNe(metaNeType: string[]) {
|
||||||
|
if (this.neList.length > 0) {
|
||||||
|
const neTypes = this.neSelectOtions.map(item => item.value);
|
||||||
|
let match = false; // 匹配
|
||||||
|
for (const netype of metaNeType) {
|
||||||
|
if (netype.indexOf('+') > -1) {
|
||||||
|
metaNeType = netype.split('+');
|
||||||
|
match = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (match) {
|
||||||
|
// 同时匹配
|
||||||
|
return metaNeType.every(item => neTypes.includes(item.toUpperCase()));
|
||||||
|
}
|
||||||
|
// 有一种
|
||||||
|
return metaNeType.some(item => neTypes.includes(item.toUpperCase()));
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
export default useNeListStore;
|
||||||
@@ -2,7 +2,6 @@ import { defineStore } from 'pinia';
|
|||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { listAllNeInfo } from '@/api/ne/neInfo';
|
import { listAllNeInfo } from '@/api/ne/neInfo';
|
||||||
import { parseDataToOptions } from '@/utils/parse-tree-utils';
|
import { parseDataToOptions } from '@/utils/parse-tree-utils';
|
||||||
import { getNeTraceInterfaceAll } from '@/api/trace/task';
|
|
||||||
import { getNePerformanceList } from '@/api/perfManage/taskManage';
|
import { getNePerformanceList } from '@/api/perfManage/taskManage';
|
||||||
|
|
||||||
/**网元信息类型 */
|
/**网元信息类型 */
|
||||||
@@ -13,8 +12,6 @@ type NeInfo = {
|
|||||||
neCascaderOptions: Record<string, any>[];
|
neCascaderOptions: Record<string, any>[];
|
||||||
/**选择器单级父类型 */
|
/**选择器单级父类型 */
|
||||||
neSelectOtions: Record<string, any>[];
|
neSelectOtions: Record<string, any>[];
|
||||||
/**跟踪接口列表 */
|
|
||||||
traceInterfaceList: Record<string, any>[];
|
|
||||||
/**性能测量数据集 */
|
/**性能测量数据集 */
|
||||||
perMeasurementList: Record<string, any>[];
|
perMeasurementList: Record<string, any>[];
|
||||||
};
|
};
|
||||||
@@ -24,7 +21,6 @@ const useNeInfoStore = defineStore('neinfo', {
|
|||||||
neList: [],
|
neList: [],
|
||||||
neCascaderOptions: [],
|
neCascaderOptions: [],
|
||||||
neSelectOtions: [],
|
neSelectOtions: [],
|
||||||
traceInterfaceList: [],
|
|
||||||
perMeasurementList: [],
|
perMeasurementList: [],
|
||||||
}),
|
}),
|
||||||
getters: {
|
getters: {
|
||||||
@@ -61,7 +57,7 @@ const useNeInfoStore = defineStore('neinfo', {
|
|||||||
const res = await listAllNeInfo({
|
const res = await listAllNeInfo({
|
||||||
bandStatus: false,
|
bandStatus: false,
|
||||||
});
|
});
|
||||||
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
|
if (res.code === RESULT_CODE_SUCCESS) {
|
||||||
// 原始列表
|
// 原始列表
|
||||||
this.neList = JSON.parse(JSON.stringify(res.data));
|
this.neList = JSON.parse(JSON.stringify(res.data));
|
||||||
|
|
||||||
@@ -79,24 +75,6 @@ const useNeInfoStore = defineStore('neinfo', {
|
|||||||
}
|
}
|
||||||
return res;
|
return res;
|
||||||
},
|
},
|
||||||
// 刷新跟踪接口列表
|
|
||||||
async fnRefreshNeTraceInterface() {
|
|
||||||
this.traceInterfaceList = [];
|
|
||||||
const res = await this.fnNeTraceInterface();
|
|
||||||
return res;
|
|
||||||
},
|
|
||||||
// 获取跟踪接口列表
|
|
||||||
async fnNeTraceInterface() {
|
|
||||||
// 有数据不请求
|
|
||||||
if (this.traceInterfaceList.length > 0) {
|
|
||||||
return { code: 1, data: this.traceInterfaceList, msg: 'success' };
|
|
||||||
}
|
|
||||||
const res = await getNeTraceInterfaceAll();
|
|
||||||
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
|
|
||||||
this.traceInterfaceList = res.data;
|
|
||||||
}
|
|
||||||
return res;
|
|
||||||
},
|
|
||||||
// 获取性能测量数据集列表
|
// 获取性能测量数据集列表
|
||||||
async fnNeTaskPerformance() {
|
async fnNeTaskPerformance() {
|
||||||
// 有数据不请求
|
// 有数据不请求
|
||||||
@@ -104,7 +82,7 @@ const useNeInfoStore = defineStore('neinfo', {
|
|||||||
return { code: 1, data: this.perMeasurementList, msg: 'success' };
|
return { code: 1, data: this.perMeasurementList, msg: 'success' };
|
||||||
}
|
}
|
||||||
const res = await getNePerformanceList();
|
const res = await getNePerformanceList();
|
||||||
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
|
if (res.code === RESULT_CODE_SUCCESS) {
|
||||||
this.perMeasurementList = res.data;
|
this.perMeasurementList = res.data;
|
||||||
}
|
}
|
||||||
return res;
|
return res;
|
||||||
|
|||||||
@@ -27,8 +27,8 @@ type UserInfo = {
|
|||||||
email: string;
|
email: string;
|
||||||
/**用户性别 */
|
/**用户性别 */
|
||||||
sex: string | undefined;
|
sex: string | undefined;
|
||||||
/**其他信息 */
|
/**用户类型 */
|
||||||
profile: Record<string, any>;
|
userType: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
const useUserStore = defineStore('user', {
|
const useUserStore = defineStore('user', {
|
||||||
@@ -42,7 +42,7 @@ const useUserStore = defineStore('user', {
|
|||||||
phonenumber: '',
|
phonenumber: '',
|
||||||
email: '',
|
email: '',
|
||||||
sex: undefined,
|
sex: undefined,
|
||||||
profile: {},
|
userType: 'System',
|
||||||
}),
|
}),
|
||||||
getters: {
|
getters: {
|
||||||
/**
|
/**
|
||||||
@@ -122,6 +122,7 @@ const useUserStore = defineStore('user', {
|
|||||||
this.phonenumber = user.phonenumber;
|
this.phonenumber = user.phonenumber;
|
||||||
this.email = user.email;
|
this.email = user.email;
|
||||||
this.sex = user.sex;
|
this.sex = user.sex;
|
||||||
|
this.userType = user.userType;
|
||||||
|
|
||||||
// 验证返回的roles是否是一个非空数组
|
// 验证返回的roles是否是一个非空数组
|
||||||
if (Array.isArray(roles) && roles.length > 0) {
|
if (Array.isArray(roles) && roles.length > 0) {
|
||||||
|
|||||||
@@ -7,8 +7,10 @@ declare module '*.vue' {
|
|||||||
export default component;
|
export default component;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// "vue3-smooth-dnd": "^0.0.6"
|
||||||
declare module 'vue3-smooth-dnd';
|
declare module 'vue3-smooth-dnd';
|
||||||
|
|
||||||
|
// "intl-tel-input": "^25.2.0"
|
||||||
declare module 'intl-tel-input/intlTelInputWithUtils' {
|
declare module 'intl-tel-input/intlTelInputWithUtils' {
|
||||||
import intlTelInput from 'intl-tel-input';
|
import intlTelInput from 'intl-tel-input';
|
||||||
export default intlTelInput;
|
export default intlTelInput;
|
||||||
|
|||||||
@@ -37,6 +37,24 @@ export async function dbGet(storeName: string, key: string) {
|
|||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**数据级缓存全部移除 */
|
||||||
|
export async function dbClear(storeName: string) {
|
||||||
|
if (!storeName ) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
localforage.config({
|
||||||
|
name: import.meta.env.VITE_APP_CODE,
|
||||||
|
storeName: storeName,
|
||||||
|
});
|
||||||
|
try {
|
||||||
|
await localforage.clear();
|
||||||
|
return true;
|
||||||
|
} catch (error) {
|
||||||
|
console.error(error);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/**数据级缓存移除 */
|
/**数据级缓存移除 */
|
||||||
export async function dbRemove(storeName: string, key: string) {
|
export async function dbRemove(storeName: string, key: string) {
|
||||||
if (!storeName || !key) {
|
if (!storeName || !key) {
|
||||||
|
|||||||
@@ -20,6 +20,13 @@ export const YYYYMMDDHHMMSS = 'YYYYMMDDHHmmss';
|
|||||||
/**年-月-日 时:分:秒 列如:2022-12-30 01:01:59 */
|
/**年-月-日 时:分:秒 列如:2022-12-30 01:01:59 */
|
||||||
export const YYYY_MM_DD_HH_MM_SS = 'YYYY-MM-DD HH:mm:ss';
|
export const YYYY_MM_DD_HH_MM_SS = 'YYYY-MM-DD HH:mm:ss';
|
||||||
|
|
||||||
|
/**特殊 列如:2025-04-28 08:00:46 GMT+08:00 */
|
||||||
|
export const YYYY_MM_DD_HH_MM_SSZ = 'YYYY-MM-DD HH:mm:ss [GMT]Z';
|
||||||
|
/**国际时间 列如:2022-12-30T01:01:59+08:00 */
|
||||||
|
export const RFC3339 = 'YYYY-MM-DDTHH:mm:ssZ';
|
||||||
|
/**国际时间 列如:Thu, Nov 14 2024 10:19 GMT+08:00 */
|
||||||
|
export const RFC822Z = 'ddd, MMM DD YYYY HH:mm [GMT]Z';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 格式时间字符串
|
* 格式时间字符串
|
||||||
* @param dateStr 时间字符串
|
* @param dateStr 时间字符串
|
||||||
@@ -36,12 +43,12 @@ export function parseStrToDate(
|
|||||||
/**
|
/**
|
||||||
* 格式时间
|
* 格式时间
|
||||||
* @param date 可转的Date对象
|
* @param date 可转的Date对象
|
||||||
* @param formatStr 时间格式 默认YYYY-MM-DD HH:mm:ss
|
* @param formatStr 时间格式 默认YYYY-MM-DD HH:mm:ssZZ
|
||||||
* @returns 时间格式字符串
|
* @returns 时间格式字符串
|
||||||
*/
|
*/
|
||||||
export function parseDateToStr(
|
export function parseDateToStr(
|
||||||
date: string | number | Date,
|
date: string | number | Date,
|
||||||
formatStr: string = YYYY_MM_DD_HH_MM_SS
|
formatStr: string = YYYY_MM_DD_HH_MM_SSZ
|
||||||
): string {
|
): string {
|
||||||
return dayjs(date).format(formatStr);
|
return dayjs(date).format(formatStr);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -42,7 +42,7 @@ export async function readLoalXlsx(
|
|||||||
/**
|
/**
|
||||||
* 读取表格数据 工作表
|
* 读取表格数据 工作表
|
||||||
* @param fileBolb 文件对象
|
* @param fileBolb 文件对象
|
||||||
* @param index 文件保存路径
|
* @param index SheetName索引
|
||||||
* @return 表格对象列表
|
* @return 表格对象列表
|
||||||
*/
|
*/
|
||||||
export async function readSheet(
|
export async function readSheet(
|
||||||
|
|||||||
@@ -13,13 +13,41 @@ export function generateColorHEX(): string {
|
|||||||
* @returns rgb(24 144 255) / rgba(0,0,0,.85)
|
* @returns rgb(24 144 255) / rgba(0,0,0,.85)
|
||||||
*/
|
*/
|
||||||
export function generateColorRGBA(hasAlpha: boolean = false) {
|
export function generateColorRGBA(hasAlpha: boolean = false) {
|
||||||
const red = Math.floor(Math.random() * 256);
|
const isDark = document.documentElement.getAttribute('data-theme') === 'dark';
|
||||||
const green = Math.floor(Math.random() * 256);
|
|
||||||
const blue = Math.floor(Math.random() * 256);
|
let red: number;
|
||||||
|
let green: number;
|
||||||
|
let blue: number;
|
||||||
|
|
||||||
|
if (isDark) {
|
||||||
|
// 暗色模式下生成较亮的颜色
|
||||||
|
red = Math.floor(Math.random() * 156) + 100; // 100-255
|
||||||
|
green = Math.floor(Math.random() * 156) + 100; // 100-255
|
||||||
|
blue = Math.floor(Math.random() * 156) + 100; // 100-255
|
||||||
|
|
||||||
|
// 确保至少有一个通道的值较高,使颜色更明亮
|
||||||
|
const brightChannel = Math.floor(Math.random() * 3);
|
||||||
|
switch (brightChannel) {
|
||||||
|
case 0:
|
||||||
|
red = Math.min(255, red + 50);
|
||||||
|
break;
|
||||||
|
case 1:
|
||||||
|
green = Math.min(255, green + 50);
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
blue = Math.min(255, blue + 50);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
// 亮色模式下生成正常的颜色
|
||||||
|
red = Math.floor(Math.random() * 256); // 0-255
|
||||||
|
green = Math.floor(Math.random() * 256); // 0-255
|
||||||
|
blue = Math.floor(Math.random() * 256); // 0-255
|
||||||
|
}
|
||||||
|
|
||||||
if (hasAlpha) {
|
if (hasAlpha) {
|
||||||
const alpha = Math.floor(Math.random() * 100);
|
const alpha = Math.floor(Math.random() * 100);
|
||||||
return `rgb(${red}, ${green}, ${blue}, 0.${alpha})`;
|
return `rgba(${red}, ${green}, ${blue}, 0.${alpha})`;
|
||||||
}
|
}
|
||||||
|
|
||||||
return `rgb(${red}, ${green}, ${blue})`;
|
return `rgb(${red}, ${green}, ${blue})`;
|
||||||
|
|||||||
@@ -126,7 +126,7 @@ export function parseDataToTreeExclude(
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 解析树结构数据转出一维id数组
|
* 解析树结构数据转出所有一维id数组
|
||||||
*
|
*
|
||||||
* @param data 数组数据
|
* @param data 数组数据
|
||||||
* @param fieldId 读取节点字段 默认 'id'
|
* @param fieldId 读取节点字段 默认 'id'
|
||||||
@@ -158,7 +158,7 @@ export function parseTreeKeys(
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 解析树结构数据转出含子节点的一维id数组
|
* 解析树结构数据转出根节点的一维id数组
|
||||||
*
|
*
|
||||||
* @param data 数组数据
|
* @param data 数组数据
|
||||||
* @param fieldId 读取节点字段 默认 'id'
|
* @param fieldId 读取节点字段 默认 'id'
|
||||||
@@ -221,3 +221,43 @@ export function parseDataToOptions(
|
|||||||
|
|
||||||
return options;
|
return options;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 解析树结构数据转出子节点关联根节点的一维id数组
|
||||||
|
*
|
||||||
|
* @param data 数组数据
|
||||||
|
* @param checkedKeys 子节点数组数据
|
||||||
|
* @param fieldId 读取节点字段 默认 'id'
|
||||||
|
* @param fieldChildren 读取子节点字段 默认 'children'
|
||||||
|
* @returns 层级数组
|
||||||
|
*/
|
||||||
|
export function parseTreeNodeKeysByChecked(
|
||||||
|
data: Record<string, any>[],
|
||||||
|
checkedKeys: (string | number)[],
|
||||||
|
fieldId: string = 'id',
|
||||||
|
fieldChildren: string = 'children'
|
||||||
|
) {
|
||||||
|
// 节点id
|
||||||
|
let treeIds: (string | number)[] = [];
|
||||||
|
componet(data);
|
||||||
|
/**闭包递归函数 */
|
||||||
|
function componet(data: Record<string, any>[]) {
|
||||||
|
if (data.length <= 0) return false;
|
||||||
|
let hasKey = false;
|
||||||
|
for (const iterator of data) {
|
||||||
|
const key = iterator[fieldId];
|
||||||
|
if (checkedKeys.includes(key)) {
|
||||||
|
hasKey = true;
|
||||||
|
}
|
||||||
|
let nodes = iterator[fieldChildren];
|
||||||
|
if (Array.isArray(nodes) && nodes.length > 0) {
|
||||||
|
if (componet(nodes)) {
|
||||||
|
treeIds.push(key);
|
||||||
|
hasKey = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return hasKey;
|
||||||
|
}
|
||||||
|
return treeIds;
|
||||||
|
}
|
||||||
@@ -172,16 +172,32 @@ export function parseSizeFromKbs(sizeByte: number, timeInterval: number): any {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* 字节数转换单位
|
* 字节数转换单位
|
||||||
* @param bits 字节Bit大小 64009540 = 512.08 MB
|
* @param byte 字节Byte大小 64009540 = 512.08 MB
|
||||||
|
* @param unit 指定单位 B / KB / MB / GB / TB / PB / EB / ZB / YB
|
||||||
* @returns xx B / KB / MB / GB / TB / PB / EB / ZB / YB
|
* @returns xx B / KB / MB / GB / TB / PB / EB / ZB / YB
|
||||||
*/
|
*/
|
||||||
export function parseSizeFromBits(bits: number | string): string {
|
export function parseSizeFromByte(
|
||||||
bits = Number(bits) || 0;
|
byte: number | string,
|
||||||
if (bits <= 0) return '0 B';
|
unit?: string
|
||||||
bits = bits * 8;
|
): string {
|
||||||
|
byte = Number(byte) || 0;
|
||||||
|
if (byte <= 0) return '0 B';
|
||||||
const units = ['B', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];
|
const units = ['B', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];
|
||||||
const unitIndex = Math.floor(Math.log2(bits) / 10);
|
let unitIndex = 0;
|
||||||
const value = (bits / Math.pow(1000, unitIndex)).toFixed(2);
|
let unitStr = 'B';
|
||||||
const unti = units[unitIndex];
|
if (unit) {
|
||||||
return `${value} ${unti}`;
|
const index = units.indexOf(unit);
|
||||||
|
if (index > -1) {
|
||||||
|
unitIndex = index;
|
||||||
|
unitStr = unit;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
unitIndex = Math.floor(Math.log2(byte) / 10);
|
||||||
|
unitStr = units[unitIndex];
|
||||||
|
}
|
||||||
|
const value = byte / Math.pow(1000, unitIndex);
|
||||||
|
if (unitIndex > 0) {
|
||||||
|
return `${value.toFixed(2)} ${unitStr}`;
|
||||||
|
}
|
||||||
|
return `${value} ${unitStr}`;
|
||||||
}
|
}
|
||||||
@@ -7,7 +7,9 @@ import StyleLayout from './components/style-layout.vue';
|
|||||||
import { useRoute } from 'vue-router';
|
import { useRoute } from 'vue-router';
|
||||||
import useAppStore from '@/store/modules/app';
|
import useAppStore from '@/store/modules/app';
|
||||||
import useI18n from '@/hooks/useI18n';
|
import useI18n from '@/hooks/useI18n';
|
||||||
|
import useUserStore from '@/store/modules/user';
|
||||||
const appStore = useAppStore();
|
const appStore = useAppStore();
|
||||||
|
const userStore = useUserStore();
|
||||||
const route = useRoute();
|
const route = useRoute();
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
|
|
||||||
@@ -29,8 +31,7 @@ onActivated(() => {
|
|||||||
// 调用时机为首次挂载
|
// 调用时机为首次挂载
|
||||||
// 以及每次从缓存中被重新插入时
|
// 以及每次从缓存中被重新插入时
|
||||||
fnLocale();
|
fnLocale();
|
||||||
})
|
});
|
||||||
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
@@ -43,12 +44,15 @@ onActivated(() => {
|
|||||||
<a-tab-pane
|
<a-tab-pane
|
||||||
key="reset-passwd"
|
key="reset-passwd"
|
||||||
:tab="t('views.account.settings.resetPasswd')"
|
:tab="t('views.account.settings.resetPasswd')"
|
||||||
|
v-if="userStore.userType === 'System'"
|
||||||
>
|
>
|
||||||
<ResetPasswd></ResetPasswd>
|
<ResetPasswd></ResetPasswd>
|
||||||
</a-tab-pane>
|
</a-tab-pane>
|
||||||
|
|
||||||
<a-tab-pane
|
<a-tab-pane
|
||||||
key="style-layout"
|
key="style-layout"
|
||||||
:tab="t('views.account.settings.styleLayout')"
|
:tab="t('views.account.settings.styleLayout')"
|
||||||
|
v-if="false"
|
||||||
>
|
>
|
||||||
<StyleLayout></StyleLayout>
|
<StyleLayout></StyleLayout>
|
||||||
</a-tab-pane>
|
</a-tab-pane>
|
||||||
|
|||||||
@@ -2,7 +2,14 @@
|
|||||||
import { PageContainer } from 'antdv-pro-layout';
|
import { PageContainer } from 'antdv-pro-layout';
|
||||||
import { ColumnsType } from 'ant-design-vue/es/table';
|
import { ColumnsType } from 'ant-design-vue/es/table';
|
||||||
import { message } from 'ant-design-vue/es';
|
import { message } from 'ant-design-vue/es';
|
||||||
import { reactive, ref, onMounted, onBeforeUnmount, markRaw } from 'vue';
|
import {
|
||||||
|
reactive,
|
||||||
|
ref,
|
||||||
|
onMounted,
|
||||||
|
onBeforeUnmount,
|
||||||
|
markRaw,
|
||||||
|
useTemplateRef,
|
||||||
|
} from 'vue';
|
||||||
import useI18n from '@/hooks/useI18n';
|
import useI18n from '@/hooks/useI18n';
|
||||||
import { TooltipComponent } from 'echarts/components';
|
import { TooltipComponent } from 'echarts/components';
|
||||||
import { GaugeChart } from 'echarts/charts';
|
import { GaugeChart } from 'echarts/charts';
|
||||||
@@ -32,24 +39,12 @@ echarts.use([
|
|||||||
]);
|
]);
|
||||||
|
|
||||||
/**图DOM节点实例对象 */
|
/**图DOM节点实例对象 */
|
||||||
const statusBar = ref<HTMLElement | undefined>(undefined);
|
const statusBar = useTemplateRef<HTMLDivElement>('statusBar');
|
||||||
|
|
||||||
/**图实例对象 */
|
/**图实例对象 */
|
||||||
const statusBarChart = ref<any>(null);
|
const statusBarChart = ref<any>(null);
|
||||||
|
|
||||||
/**网元状态字典数据 */
|
|
||||||
let indexColor = ref<DictType[]>([
|
|
||||||
{ label: 'Normal', value: 'normal', tagType: '', tagClass: '#91cc75' },
|
|
||||||
{
|
|
||||||
label: 'Abnormal',
|
|
||||||
value: 'abnormal',
|
|
||||||
tagType: '',
|
|
||||||
tagClass: '#ee6666',
|
|
||||||
},
|
|
||||||
]);
|
|
||||||
|
|
||||||
/**表格字段列 */
|
/**表格字段列 */
|
||||||
//customRender(){} ----单元格处理
|
|
||||||
let tableColumns: ColumnsType = [
|
let tableColumns: ColumnsType = [
|
||||||
{
|
{
|
||||||
title: t('views.index.object'),
|
title: t('views.index.object'),
|
||||||
@@ -67,7 +62,9 @@ let tableColumns: ColumnsType = [
|
|||||||
dataIndex: 'serverState',
|
dataIndex: 'serverState',
|
||||||
align: 'left',
|
align: 'left',
|
||||||
customRender(opt) {
|
customRender(opt) {
|
||||||
if (opt.value?.refreshTime) return parseDateToStr(opt.value?.refreshTime);
|
if (opt.value?.refreshTime) {
|
||||||
|
return parseDateToStr(opt.value?.refreshTime, 'HH:mm:ss');
|
||||||
|
}
|
||||||
return '-';
|
return '-';
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
@@ -104,12 +101,13 @@ let tableColumns: ColumnsType = [
|
|||||||
},
|
},
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
|
|
||||||
/**表格状态类型 */
|
/**表格状态类型 */
|
||||||
type TabeStateType = {
|
type TabeStateType = {
|
||||||
/**加载等待 */
|
/**加载等待 */
|
||||||
loading: boolean;
|
loading: boolean;
|
||||||
/**记录数据 */
|
/**记录数据 */
|
||||||
data: object[];
|
data: Record<string, any>[];
|
||||||
/**勾选记录 */
|
/**勾选记录 */
|
||||||
selectedRowKeys: (string | number)[];
|
selectedRowKeys: (string | number)[];
|
||||||
};
|
};
|
||||||
@@ -121,114 +119,84 @@ let tableState: TabeStateType = reactive({
|
|||||||
selectedRowKeys: [],
|
selectedRowKeys: [],
|
||||||
});
|
});
|
||||||
|
|
||||||
/**表格状态 */
|
/**状态 */
|
||||||
let nfInfo: any = reactive({
|
let serverState: any = ref({});
|
||||||
obj: 'OMC',
|
|
||||||
version: appStore.version,
|
|
||||||
status: t('views.index.normal'),
|
|
||||||
outTimeDate: '',
|
|
||||||
serialNum: appStore.serialNum,
|
|
||||||
});
|
|
||||||
|
|
||||||
/**表格状态类型 */
|
|
||||||
type nfStateType = {
|
|
||||||
/**主机名 */
|
|
||||||
hostName: string;
|
|
||||||
/**操作系统信息 */
|
|
||||||
osInfo: string;
|
|
||||||
/**IP地址 */
|
|
||||||
ipAddress: string;
|
|
||||||
/**版本 */
|
|
||||||
version: string;
|
|
||||||
/**CPU利用率 */
|
|
||||||
cpuUse: string;
|
|
||||||
/**内存使用 */
|
|
||||||
memoryUse: string;
|
|
||||||
/**用户容量 */
|
|
||||||
capability: number;
|
|
||||||
/**序列号 */
|
|
||||||
serialNum: string;
|
|
||||||
/**许可证到期日期 */
|
|
||||||
/* selectedRowKeys: (string | number)[];*/
|
|
||||||
expiryDate: string;
|
|
||||||
};
|
|
||||||
/**网元详细信息 */
|
|
||||||
let pronInfo: nfStateType = reactive({
|
|
||||||
hostName: '5gc',
|
|
||||||
osInfo: 'Linux 5gc 4.15.0-112-generic 2020 x86_64 GNU/Linux',
|
|
||||||
ipAddress: '-',
|
|
||||||
version: '-',
|
|
||||||
cpuUse: '-',
|
|
||||||
memoryUse: '-',
|
|
||||||
capability: 0,
|
|
||||||
serialNum: '-',
|
|
||||||
expiryDate: '-',
|
|
||||||
});
|
|
||||||
|
|
||||||
/**查询网元状态列表 */
|
/**查询网元状态列表 */
|
||||||
function fnGetList(one: boolean) {
|
async function fnGetList(reload: boolean = false) {
|
||||||
if (tableState.loading) return;
|
tableState.loading = !reload;
|
||||||
one && (tableState.loading = true);
|
try {
|
||||||
listAllNeInfo({ bandStatus: true }).then(res => {
|
const res = await listAllNeInfo({ bandStatus: true });
|
||||||
tableState.data = res.data;
|
tableState.data = res.data;
|
||||||
tableState.loading = false;
|
} catch (error) {
|
||||||
var rightNum = 0;
|
console.error(error);
|
||||||
var errorNum = 0;
|
tableState.data = [];
|
||||||
res.data.forEach((item: any) => {
|
}
|
||||||
if (item.serverState.online) {
|
tableState.loading = false;
|
||||||
rightNum++;
|
if (tableState.data.length == 0) {
|
||||||
} else {
|
return;
|
||||||
errorNum++;
|
}
|
||||||
}
|
|
||||||
});
|
var rightNum = 0;
|
||||||
const optionData: any = {
|
var errorNum = 0;
|
||||||
title: {
|
for (const v of tableState.data) {
|
||||||
text: '',
|
if (v?.serverState?.online) {
|
||||||
subtext: '',
|
rightNum++;
|
||||||
left: 'center',
|
} else {
|
||||||
},
|
errorNum++;
|
||||||
tooltip: {
|
}
|
||||||
trigger: 'item',
|
}
|
||||||
},
|
|
||||||
legend: {
|
// 初始
|
||||||
orient: 'vertical',
|
if (!reload) {
|
||||||
left: 'left',
|
if (statusBar.value) {
|
||||||
},
|
fnDesign(statusBar.value, rightNum, errorNum);
|
||||||
color: indexColor.value.map(item => item.tagClass),
|
}
|
||||||
|
} else {
|
||||||
|
statusBarChart.value.setOption({
|
||||||
series: [
|
series: [
|
||||||
{
|
{
|
||||||
name: t('views.index.realNeStatus'),
|
|
||||||
type: 'pie',
|
|
||||||
radius: '70%',
|
|
||||||
center: ['50%', '50%'],
|
|
||||||
data: [
|
data: [
|
||||||
{ value: rightNum, name: t('views.index.normal') },
|
{ value: rightNum, name: t('views.index.normal') },
|
||||||
{ value: errorNum, name: t('views.index.abnormal') },
|
{ value: errorNum, name: t('views.index.abnormal') },
|
||||||
],
|
],
|
||||||
emphasis: {
|
|
||||||
itemStyle: {
|
|
||||||
shadowBlur: 10,
|
|
||||||
shadowOffsetX: 0,
|
|
||||||
shadowColor: 'rgba(0, 0, 0, 0.5)',
|
|
||||||
},
|
|
||||||
},
|
|
||||||
|
|
||||||
label: {},
|
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
};
|
});
|
||||||
|
}
|
||||||
fnDesign(statusBar.value, optionData);
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function fnDesign(container: HTMLElement | undefined, option: any) {
|
function fnDesign(container: HTMLElement, rightNum: number, errorNum: number) {
|
||||||
if (!container) return;
|
/// 图表数据
|
||||||
|
const optionData: any = {
|
||||||
if (!statusBarChart.value) {
|
title: {
|
||||||
statusBarChart.value = markRaw(echarts.init(container, 'light'));
|
text: '',
|
||||||
}
|
subtext: '',
|
||||||
option && statusBarChart.value.setOption(option);
|
left: 'center',
|
||||||
|
},
|
||||||
|
tooltip: {
|
||||||
|
trigger: 'item',
|
||||||
|
},
|
||||||
|
legend: {
|
||||||
|
orient: 'vertical',
|
||||||
|
left: 'left',
|
||||||
|
},
|
||||||
|
color: dict.indexStatus.map(item => item.tagClass),
|
||||||
|
series: [
|
||||||
|
{
|
||||||
|
name: t('views.index.runStatus'),
|
||||||
|
type: 'pie',
|
||||||
|
radius: '70%',
|
||||||
|
center: ['50%', '50%'],
|
||||||
|
data: [
|
||||||
|
{ value: rightNum, name: t('views.index.normal') },
|
||||||
|
{ value: errorNum, name: t('views.index.abnormal') },
|
||||||
|
],
|
||||||
|
},
|
||||||
|
],
|
||||||
|
};
|
||||||
|
statusBarChart.value = markRaw(echarts.init(container, 'light'));
|
||||||
|
statusBarChart.value.setOption(optionData);
|
||||||
|
|
||||||
// 创建 ResizeObserver 实例
|
// 创建 ResizeObserver 实例
|
||||||
var observer = new ResizeObserver(entries => {
|
var observer = new ResizeObserver(entries => {
|
||||||
@@ -240,67 +208,6 @@ function fnDesign(container: HTMLElement | undefined, option: any) {
|
|||||||
observer.observe(container);
|
observer.observe(container);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**抽屉 网元详细信息 */
|
|
||||||
const open = ref(false);
|
|
||||||
const closeDrawer = () => {
|
|
||||||
open.value = false;
|
|
||||||
};
|
|
||||||
/**抽屉 网元详细信息 */
|
|
||||||
|
|
||||||
/**监听表格行事件*/
|
|
||||||
function rowClick(record: any, index: any) {
|
|
||||||
return {
|
|
||||||
onClick: (event: any) => {
|
|
||||||
let pronData = JSON.parse(JSON.stringify(record.serverState));
|
|
||||||
if (!pronData.online) {
|
|
||||||
message.error(t('views.index.neStatus'), 2);
|
|
||||||
return false;
|
|
||||||
} else {
|
|
||||||
const totalMemInKB = pronData.mem?.totalMem;
|
|
||||||
const nfUsedMemInKB = pronData.mem?.nfUsedMem;
|
|
||||||
const sysMemUsageInKB = pronData.mem?.sysMemUsage;
|
|
||||||
|
|
||||||
// 将KB转换为MB
|
|
||||||
const totalMemInMB = Math.round((totalMemInKB / 1024) * 100) / 100;
|
|
||||||
const nfUsedMemInMB = Math.round((nfUsedMemInKB / 1024) * 100) / 100;
|
|
||||||
const sysMemUsageInMB =
|
|
||||||
Math.round((sysMemUsageInKB / 1024) * 100) / 100;
|
|
||||||
|
|
||||||
//渲染详细信息
|
|
||||||
pronInfo = {
|
|
||||||
hostName: pronData.hostname,
|
|
||||||
osInfo: pronData.os,
|
|
||||||
ipAddress: pronData.neIP,
|
|
||||||
version: pronData.version,
|
|
||||||
cpuUse:
|
|
||||||
pronData.neName +
|
|
||||||
':' +
|
|
||||||
pronData.cpu?.nfCpuUsage / 100 +
|
|
||||||
'%; ' +
|
|
||||||
'SYS:' +
|
|
||||||
pronData.cpu?.sysCpuUsage / 100 +
|
|
||||||
'%',
|
|
||||||
memoryUse:
|
|
||||||
'Total:' +
|
|
||||||
totalMemInMB +
|
|
||||||
'MB; ' +
|
|
||||||
pronData.name +
|
|
||||||
':' +
|
|
||||||
nfUsedMemInMB +
|
|
||||||
'MB; SYS:' +
|
|
||||||
sysMemUsageInMB +
|
|
||||||
'MB',
|
|
||||||
capability: pronData.capability,
|
|
||||||
serialNum: pronData.sn,
|
|
||||||
expiryDate: pronData.expire,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
open.value = true;
|
|
||||||
},
|
|
||||||
};
|
|
||||||
}
|
|
||||||
let timer: any;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 国际化翻译转换
|
* 国际化翻译转换
|
||||||
*/
|
*/
|
||||||
@@ -312,63 +219,50 @@ function fnLocale() {
|
|||||||
appStore.setTitle(title);
|
appStore.setTitle(title);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**字典数据 */
|
||||||
|
let dict: {
|
||||||
|
/**网元信息状态 */
|
||||||
|
neInfoStatus: DictType[];
|
||||||
|
/**主页状态 */
|
||||||
|
indexStatus: DictType[];
|
||||||
|
} = reactive({
|
||||||
|
neInfoStatus: [],
|
||||||
|
indexStatus: [],
|
||||||
|
});
|
||||||
|
|
||||||
|
let timer: any;
|
||||||
|
let timerFlag: boolean = false;
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
getDict('index_status')
|
// 初始字典数据
|
||||||
.then(res => {
|
Promise.allSettled([getDict('ne_info_status'), getDict('index_status')])
|
||||||
if (res.length > 0) {
|
.then(resArr => {
|
||||||
indexColor.value = res;
|
if (resArr[0].status === 'fulfilled') {
|
||||||
|
dict.neInfoStatus = resArr[0].value;
|
||||||
|
}
|
||||||
|
if (resArr[1].status === 'fulfilled') {
|
||||||
|
dict.indexStatus = resArr[1].value;
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.finally(() => {
|
.finally(async () => {
|
||||||
fnLocale();
|
fnLocale();
|
||||||
fnGetList(true);
|
await fnGetList(false);
|
||||||
timer = setInterval(() => fnGetList(false), 10000); // 每隔10秒执行一次
|
timer = setInterval(() => {
|
||||||
|
if (timerFlag) return;
|
||||||
|
fnGetList(true);
|
||||||
|
}, 10_000); // 每隔10秒执行一次
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
// 在组件卸载之前清除定时器
|
// 在组件卸载之前清除定时器
|
||||||
|
|
||||||
onBeforeUnmount(() => {
|
onBeforeUnmount(() => {
|
||||||
clearInterval(timer);
|
clearInterval(timer);
|
||||||
|
timer = null;
|
||||||
|
timerFlag = true;
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<template>
|
<template>
|
||||||
<PageContainer :breadcrumb="{}">
|
<PageContainer :breadcrumb="{}">
|
||||||
<div>
|
|
||||||
<a-drawer :open="open" @close="closeDrawer" :width="700">
|
|
||||||
<a-descriptions bordered :column="1" :label-style="{ width: '160px' }">
|
|
||||||
<a-descriptions-item :label="t('views.index.hostName')">{{
|
|
||||||
pronInfo.hostName
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.osInfo')">{{
|
|
||||||
pronInfo.osInfo
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.ipAddress')">{{
|
|
||||||
pronInfo.ipAddress
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.version')">{{
|
|
||||||
pronInfo.version
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.capability')">{{
|
|
||||||
pronInfo.capability
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.cpuUse')">{{
|
|
||||||
pronInfo.cpuUse
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.memoryUse')">{{
|
|
||||||
pronInfo.memoryUse
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.serialNum')">{{
|
|
||||||
pronInfo.serialNum
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.expiryDate')">{{
|
|
||||||
pronInfo.expiryDate
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
</a-descriptions>
|
|
||||||
</a-drawer>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<a-row :gutter="16">
|
<a-row :gutter="16">
|
||||||
<a-col :lg="14" :md="16" :xs="24">
|
<a-col :lg="14" :md="16" :xs="24">
|
||||||
<!-- 表格列表 -->
|
<!-- 表格列表 -->
|
||||||
@@ -377,20 +271,14 @@ onBeforeUnmount(() => {
|
|||||||
row-key="id"
|
row-key="id"
|
||||||
size="small"
|
size="small"
|
||||||
:columns="tableColumns"
|
:columns="tableColumns"
|
||||||
:loading="tableState.loading"
|
|
||||||
:data-source="tableState.data"
|
:data-source="tableState.data"
|
||||||
|
:loading="tableState.loading"
|
||||||
:pagination="false"
|
:pagination="false"
|
||||||
:scroll="{ x: true }"
|
:scroll="{ x: true }"
|
||||||
:customRow="rowClick"
|
|
||||||
>
|
>
|
||||||
<template #bodyCell="{ column, record }">
|
<template #bodyCell="{ column, record }">
|
||||||
<template v-if="column.key === 'status'">
|
<template v-if="column.key === 'status'">
|
||||||
<div v-if="record.serverState.online">
|
<DictTag :options="dict.neInfoStatus" :value="record.status" />
|
||||||
<a-tag color="blue">{{ t('views.index.normal') }}</a-tag>
|
|
||||||
</div>
|
|
||||||
<div v-else>
|
|
||||||
<a-tag color="pink">{{ t('views.index.abnormal') }}</a-tag>
|
|
||||||
</div>
|
|
||||||
</template>
|
</template>
|
||||||
</template>
|
</template>
|
||||||
</a-table>
|
</a-table>
|
||||||
@@ -403,37 +291,6 @@ onBeforeUnmount(() => {
|
|||||||
>
|
>
|
||||||
<div style="width: 100%; min-height: 200px" ref="statusBar"></div>
|
<div style="width: 100%; min-height: 200px" ref="statusBar"></div>
|
||||||
</a-card>
|
</a-card>
|
||||||
<a-card
|
|
||||||
:title="t('views.index.mark')"
|
|
||||||
style="margin-top: 16px"
|
|
||||||
size="small"
|
|
||||||
>
|
|
||||||
<a-descriptions
|
|
||||||
bordered
|
|
||||||
:column="1"
|
|
||||||
:label-style="{ width: '160px' }"
|
|
||||||
>
|
|
||||||
<a-descriptions-item :label="t('views.index.object')">{{
|
|
||||||
nfInfo.obj
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<template v-if="nfInfo.obj === 'OMC'">
|
|
||||||
<a-descriptions-item :label="t('views.index.versionNum')">{{
|
|
||||||
nfInfo.version
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.systemStatus')">{{
|
|
||||||
nfInfo.status
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
</template>
|
|
||||||
<template v-else>
|
|
||||||
<a-descriptions-item :label="t('views.index.serialNum')">{{
|
|
||||||
nfInfo.serialNum
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
<a-descriptions-item :label="t('views.index.expiryDate')">{{
|
|
||||||
nfInfo.outTimeDate
|
|
||||||
}}</a-descriptions-item>
|
|
||||||
</template>
|
|
||||||
</a-descriptions>
|
|
||||||
</a-card>
|
|
||||||
</a-col>
|
</a-col>
|
||||||
</a-row>
|
</a-row>
|
||||||
</PageContainer>
|
</PageContainer>
|
||||||
|
|||||||
@@ -5,20 +5,31 @@ import { message, Modal } from 'ant-design-vue/es';
|
|||||||
import { SizeType } from 'ant-design-vue/es/config-provider';
|
import { SizeType } from 'ant-design-vue/es/config-provider';
|
||||||
import { MenuInfo } from 'ant-design-vue/es/menu/src/interface';
|
import { MenuInfo } from 'ant-design-vue/es/menu/src/interface';
|
||||||
import { ColumnsType } from 'ant-design-vue/es/table';
|
import { ColumnsType } from 'ant-design-vue/es/table';
|
||||||
|
import TableColumnsDnd from '@/components/TableColumnsDnd/index.vue';
|
||||||
import useI18n from '@/hooks/useI18n';
|
import useI18n from '@/hooks/useI18n';
|
||||||
import {
|
import {
|
||||||
RESULT_CODE_ERROR,
|
RESULT_CODE_ERROR,
|
||||||
RESULT_CODE_SUCCESS,
|
RESULT_CODE_SUCCESS,
|
||||||
} from '@/constants/result-constants';
|
} from '@/constants/result-constants';
|
||||||
import useDictStore from '@/store/modules/dict';
|
import useDictStore from '@/store/modules/dict';
|
||||||
|
import useNeInfoStore from '@/store/modules/neinfo';
|
||||||
import { listAMFDataUE, delAMFDataUE, exportAMFDataUE } from '@/api/neData/amf';
|
import { listAMFDataUE, delAMFDataUE, exportAMFDataUE } from '@/api/neData/amf';
|
||||||
|
import { parseDateToStr } from '@/utils/date-utils';
|
||||||
import { OptionsType, WS } from '@/plugins/ws-websocket';
|
import { OptionsType, WS } from '@/plugins/ws-websocket';
|
||||||
|
import dayjs, { Dayjs } from 'dayjs';
|
||||||
import saveAs from 'file-saver';
|
import saveAs from 'file-saver';
|
||||||
import PQueue from 'p-queue';
|
import PQueue from 'p-queue';
|
||||||
|
import useUserStore from '@/store/modules/user';
|
||||||
|
import { TENANTADMIN_ROLE_KEY } from '@/constants/admin-constants';
|
||||||
|
import { listTenant } from '@/api/system/tenant';
|
||||||
|
import { useClipboard } from '@vueuse/core';
|
||||||
|
const { copy } = useClipboard({ legacy: true });
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const { getDict } = useDictStore();
|
const { getDict } = useDictStore();
|
||||||
const ws = new WS();
|
const ws = new WS();
|
||||||
const queue = new PQueue({ concurrency: 1, autoStart: true });
|
const queue = new PQueue({ concurrency: 1, autoStart: true });
|
||||||
|
/**网元可选 */
|
||||||
|
let neOtions = ref<Record<string, any>[]>([]);
|
||||||
|
|
||||||
/**字典数据 */
|
/**字典数据 */
|
||||||
let dict: {
|
let dict: {
|
||||||
@@ -35,21 +46,26 @@ let dict: {
|
|||||||
});
|
});
|
||||||
|
|
||||||
/**开始结束时间 */
|
/**开始结束时间 */
|
||||||
let queryRangePicker = ref<[string, string]>(['', '']);
|
let queryRangePicker = ref<[Dayjs, Dayjs] | undefined>([
|
||||||
|
dayjs().startOf('hour'),
|
||||||
|
dayjs().endOf('hour'),
|
||||||
|
]);
|
||||||
|
|
||||||
/**查询参数 */
|
/**查询参数 */
|
||||||
let queryParams = reactive({
|
let queryParams = reactive({
|
||||||
|
tenantNameArr: <Record<string, any>[]>[],
|
||||||
/**网元类型 */
|
/**网元类型 */
|
||||||
neType: 'AMF',
|
neType: 'AMF',
|
||||||
neId: '001',
|
neId: '001',
|
||||||
eventType: '',
|
eventType: '',
|
||||||
imsi: '',
|
imsi: '',
|
||||||
|
tenantName: '',
|
||||||
sortField: 'timestamp',
|
sortField: 'timestamp',
|
||||||
sortOrder: 'desc',
|
sortOrder: 'desc',
|
||||||
/**开始时间 */
|
/**开始时间 */
|
||||||
startTime: '',
|
startTime: undefined as undefined | number,
|
||||||
/**结束时间 */
|
/**结束时间 */
|
||||||
endTime: '',
|
endTime: undefined as undefined | number,
|
||||||
/**当前页数 */
|
/**当前页数 */
|
||||||
pageNum: 1,
|
pageNum: 1,
|
||||||
/**每页条数 */
|
/**每页条数 */
|
||||||
@@ -62,12 +78,13 @@ function fnQueryReset() {
|
|||||||
queryParams = Object.assign(queryParams, {
|
queryParams = Object.assign(queryParams, {
|
||||||
eventType: '',
|
eventType: '',
|
||||||
imsi: '',
|
imsi: '',
|
||||||
startTime: '',
|
tenantName: '',
|
||||||
endTime: '',
|
startTime: 0,
|
||||||
|
endTime: 0,
|
||||||
pageNum: 1,
|
pageNum: 1,
|
||||||
pageSize: 20,
|
pageSize: 20,
|
||||||
});
|
});
|
||||||
queryRangePicker.value = ['', ''];
|
queryRangePicker.value = [dayjs().startOf('hour'), dayjs().endOf('hour')];
|
||||||
tablePagination.current = 1;
|
tablePagination.current = 1;
|
||||||
tablePagination.pageSize = 20;
|
tablePagination.pageSize = 20;
|
||||||
fnGetList();
|
fnGetList();
|
||||||
@@ -106,14 +123,17 @@ let tableState: TabeStateType = reactive({
|
|||||||
selectedRowKeys: [],
|
selectedRowKeys: [],
|
||||||
});
|
});
|
||||||
|
|
||||||
|
/**表格字段列排序 */
|
||||||
|
let tableColumnsDnd = ref<ColumnsType>([]);
|
||||||
|
|
||||||
/**表格字段列 */
|
/**表格字段列 */
|
||||||
let tableColumns: ColumnsType = [
|
let tableColumns: ColumnsType = [
|
||||||
{
|
// {
|
||||||
title: t('common.rowId'),
|
// title: t('common.rowId'),
|
||||||
dataIndex: 'id',
|
// dataIndex: 'id',
|
||||||
align: 'left',
|
// align: 'left',
|
||||||
width: 100,
|
// width: 100,
|
||||||
},
|
// },
|
||||||
{
|
{
|
||||||
title: 'IMSI',
|
title: 'IMSI',
|
||||||
dataIndex: 'eventJSON',
|
dataIndex: 'eventJSON',
|
||||||
@@ -141,8 +161,25 @@ let tableColumns: ColumnsType = [
|
|||||||
{
|
{
|
||||||
title: t('views.dashboard.ue.time'),
|
title: t('views.dashboard.ue.time'),
|
||||||
dataIndex: 'eventJSON',
|
dataIndex: 'eventJSON',
|
||||||
key: 'time',
|
|
||||||
align: 'left',
|
align: 'left',
|
||||||
|
width: 250,
|
||||||
|
customRender(opt) {
|
||||||
|
const record = opt.value;
|
||||||
|
console.log(record);
|
||||||
|
if (record?.time) {
|
||||||
|
return parseDateToStr(record.time);
|
||||||
|
}
|
||||||
|
if (record?.timestamp) {
|
||||||
|
return parseDateToStr(+record.timestamp * 1000);
|
||||||
|
}
|
||||||
|
return '';
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: t('views.dashboard.cdr.tenantName'),
|
||||||
|
dataIndex: 'tenantName',
|
||||||
|
align: 'center',
|
||||||
|
key: 'tenantName',
|
||||||
width: 150,
|
width: 150,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
@@ -252,11 +289,19 @@ function fnGetList(pageNum?: number) {
|
|||||||
if (pageNum) {
|
if (pageNum) {
|
||||||
queryParams.pageNum = pageNum;
|
queryParams.pageNum = pageNum;
|
||||||
}
|
}
|
||||||
if (!queryRangePicker.value) {
|
|
||||||
queryRangePicker.value = ['', ''];
|
// 时间范围
|
||||||
|
if (
|
||||||
|
Array.isArray(queryRangePicker.value) &&
|
||||||
|
queryRangePicker.value.length > 0
|
||||||
|
) {
|
||||||
|
queryParams.startTime = queryRangePicker.value[0].valueOf();
|
||||||
|
queryParams.endTime = queryRangePicker.value[1].valueOf();
|
||||||
|
} else {
|
||||||
|
queryParams.startTime = undefined;
|
||||||
|
queryParams.endTime = undefined;
|
||||||
}
|
}
|
||||||
queryParams.startTime = queryRangePicker.value[0];
|
|
||||||
queryParams.endTime = queryRangePicker.value[1];
|
|
||||||
listAMFDataUE(toRaw(queryParams)).then(res => {
|
listAMFDataUE(toRaw(queryParams)).then(res => {
|
||||||
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.rows)) {
|
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.rows)) {
|
||||||
// 取消勾选
|
// 取消勾选
|
||||||
@@ -293,14 +338,18 @@ function fnGetList(pageNum?: number) {
|
|||||||
|
|
||||||
/**列表导出 */
|
/**列表导出 */
|
||||||
function fnExportList() {
|
function fnExportList() {
|
||||||
if (modalState.confirmLoading) return;
|
if (modalState.confirmLoading || tablePagination.total === 0) return;
|
||||||
Modal.confirm({
|
Modal.confirm({
|
||||||
title: t('common.tipTitle'),
|
title: t('common.tipTitle'),
|
||||||
content: t('views.dashboard.ue.exportTip'),
|
content: t('views.dashboard.ue.exportTip'),
|
||||||
onOk() {
|
onOk() {
|
||||||
|
modalState.confirmLoading = true;
|
||||||
const hide = message.loading(t('common.loading'), 0);
|
const hide = message.loading(t('common.loading'), 0);
|
||||||
const querys = toRaw(queryParams);
|
const querys = toRaw(queryParams);
|
||||||
querys.pageSize = 10000;
|
querys.pageNum = 1;
|
||||||
|
querys.pageSize = tablePagination.total;
|
||||||
|
querys.startTime = Number(querys.startTime);
|
||||||
|
querys.endTime = Number(querys.endTime);
|
||||||
exportAMFDataUE(querys)
|
exportAMFDataUE(querys)
|
||||||
.then(res => {
|
.then(res => {
|
||||||
if (res.code === RESULT_CODE_SUCCESS) {
|
if (res.code === RESULT_CODE_SUCCESS) {
|
||||||
@@ -324,6 +373,18 @@ function fnExportList() {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 复制CDR
|
||||||
|
* @param jsonStr JSON字符串
|
||||||
|
*/
|
||||||
|
function fnRecordCopy(jsonStr: string) {
|
||||||
|
if (!jsonStr) return;
|
||||||
|
const text = JSON.stringify(jsonStr, null, 2);
|
||||||
|
copy(text).then(() => {
|
||||||
|
message.success(t('common.copyOk'), 3);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
/**实时数据开关 */
|
/**实时数据开关 */
|
||||||
const realTimeData = ref<boolean>(false);
|
const realTimeData = ref<boolean>(false);
|
||||||
|
|
||||||
@@ -333,31 +394,30 @@ const realTimeData = ref<boolean>(false);
|
|||||||
function fnRealTime() {
|
function fnRealTime() {
|
||||||
realTimeData.value = !realTimeData.value;
|
realTimeData.value = !realTimeData.value;
|
||||||
if (realTimeData.value) {
|
if (realTimeData.value) {
|
||||||
|
tableState.seached = false;
|
||||||
// 建立链接
|
// 建立链接
|
||||||
const options: OptionsType = {
|
const options: OptionsType = {
|
||||||
url: '/ws',
|
url: '/ws',
|
||||||
params: {
|
params: {
|
||||||
/**订阅通道组
|
/**订阅通道组
|
||||||
*
|
*
|
||||||
* AMF_UE会话事件(GroupID:1010)
|
* AMF_UE会话事件(GroupID:1010_neId)
|
||||||
*/
|
*/
|
||||||
subGroupID: '1010',
|
subGroupID: `1010_${queryParams.neId}`,
|
||||||
},
|
},
|
||||||
onmessage: wsMessage,
|
onmessage: wsMessage,
|
||||||
onerror: wsError,
|
onerror: (ev: any) => {
|
||||||
|
console.error(ev);
|
||||||
|
},
|
||||||
};
|
};
|
||||||
ws.connect(options);
|
ws.connect(options);
|
||||||
} else {
|
} else {
|
||||||
ws.close();
|
ws.close();
|
||||||
|
tableState.seached = true;
|
||||||
|
fnGetList(1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**接收数据后回调 */
|
|
||||||
function wsError(ev: any) {
|
|
||||||
// 接收数据后回调
|
|
||||||
console.error(ev);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**接收数据后回调 */
|
/**接收数据后回调 */
|
||||||
function wsMessage(res: Record<string, any>) {
|
function wsMessage(res: Record<string, any>) {
|
||||||
const { code, requestId, data } = res;
|
const { code, requestId, data } = res;
|
||||||
@@ -371,7 +431,7 @@ function wsMessage(res: Record<string, any>) {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// ueEvent AMF_UE会话事件
|
// ueEvent AMF_UE会话事件
|
||||||
if (data.groupId === '1010') {
|
if (data.groupId === `1010_${queryParams.neId}`) {
|
||||||
const ueEvent = data.data;
|
const ueEvent = data.data;
|
||||||
queue.add(async () => {
|
queue.add(async () => {
|
||||||
modalState.maxId += 1;
|
modalState.maxId += 1;
|
||||||
@@ -399,22 +459,71 @@ onMounted(() => {
|
|||||||
getDict('ue_auth_code'),
|
getDict('ue_auth_code'),
|
||||||
getDict('ue_event_type'),
|
getDict('ue_event_type'),
|
||||||
getDict('ue_event_cm_state'),
|
getDict('ue_event_cm_state'),
|
||||||
])
|
]).then(resArr => {
|
||||||
.then(resArr => {
|
if (resArr[0].status === 'fulfilled') {
|
||||||
if (resArr[0].status === 'fulfilled') {
|
dict.ueAauthCode = resArr[0].value;
|
||||||
dict.ueAauthCode = resArr[0].value;
|
}
|
||||||
}
|
if (resArr[1].status === 'fulfilled') {
|
||||||
if (resArr[1].status === 'fulfilled') {
|
dict.ueEventType = resArr[1].value;
|
||||||
dict.ueEventType = resArr[1].value;
|
}
|
||||||
}
|
if (resArr[2].status === 'fulfilled') {
|
||||||
if (resArr[2].status === 'fulfilled') {
|
dict.ueEventCmState = resArr[2].value;
|
||||||
dict.ueEventCmState = resArr[2].value;
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// 获取网元网元列表
|
||||||
|
useNeInfoStore()
|
||||||
|
.fnNelist()
|
||||||
|
.then(res => {
|
||||||
|
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
|
||||||
|
if (res.data.length > 0) {
|
||||||
|
let arr: Record<string, any>[] = [];
|
||||||
|
res.data.forEach(i => {
|
||||||
|
if (i.neType === 'AMF') {
|
||||||
|
arr.push({ value: i.neId, label: i.neName });
|
||||||
|
}
|
||||||
|
});
|
||||||
|
neOtions.value = arr;
|
||||||
|
if (arr.length > 0) {
|
||||||
|
queryParams.neId = arr[0].value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
message.warning({
|
||||||
|
content: t('common.noData'),
|
||||||
|
duration: 2,
|
||||||
|
});
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
.finally(() => {
|
.finally(() => {
|
||||||
// 获取列表数据
|
// 获取列表数据
|
||||||
|
if (useUserStore().roles.includes('tenant')) {
|
||||||
|
const operateColumnIndex = tableColumns.findIndex(
|
||||||
|
column => column.key === 'tenantName'
|
||||||
|
);
|
||||||
|
|
||||||
|
if (operateColumnIndex !== -1) {
|
||||||
|
tableColumns.splice(operateColumnIndex, 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fnGetList();
|
fnGetList();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
//查询租户
|
||||||
|
listTenant({ parentId: 0 }).then(res => {
|
||||||
|
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
|
||||||
|
queryParams.tenantNameArr = []; //上面置为空数组时会报错 故在此
|
||||||
|
res.data.forEach((item: any) => {
|
||||||
|
if (item.parentId === '0') {
|
||||||
|
queryParams.tenantNameArr.push({
|
||||||
|
value: item.tenantName,
|
||||||
|
label: item.tenantName,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
onBeforeUnmount(() => {
|
onBeforeUnmount(() => {
|
||||||
@@ -434,6 +543,16 @@ onBeforeUnmount(() => {
|
|||||||
<!-- 表格搜索栏 -->
|
<!-- 表格搜索栏 -->
|
||||||
<a-form :model="queryParams" name="queryParams" layout="horizontal">
|
<a-form :model="queryParams" name="queryParams" layout="horizontal">
|
||||||
<a-row :gutter="16">
|
<a-row :gutter="16">
|
||||||
|
<a-col :lg="6" :md="12" :xs="24">
|
||||||
|
<a-form-item label="AMF" name="neId ">
|
||||||
|
<a-select
|
||||||
|
v-model:value="queryParams.neId"
|
||||||
|
:options="neOtions"
|
||||||
|
:placeholder="t('common.selectPlease')"
|
||||||
|
@change="fnGetList(1)"
|
||||||
|
/>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
<a-col :lg="6" :md="12" :xs="24">
|
<a-col :lg="6" :md="12" :xs="24">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
:label="t('views.dashboard.ue.eventType')"
|
:label="t('views.dashboard.ue.eventType')"
|
||||||
@@ -448,7 +567,7 @@ onBeforeUnmount(() => {
|
|||||||
></a-select>
|
></a-select>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col :lg="4" :md="12" :xs="24">
|
<a-col :lg="6" :md="12" :xs="24">
|
||||||
<a-form-item label="IMSI" name="imsi ">
|
<a-form-item label="IMSI" name="imsi ">
|
||||||
<a-input
|
<a-input
|
||||||
v-model:value="queryParams.imsi"
|
v-model:value="queryParams.imsi"
|
||||||
@@ -457,6 +576,31 @@ onBeforeUnmount(() => {
|
|||||||
></a-input>
|
></a-input>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
|
<a-col :lg="6" :md="12" :xs="24" v-roles:has="[TENANTADMIN_ROLE_KEY]">
|
||||||
|
<a-form-item
|
||||||
|
:label="t('views.neUser.sub.tenantName')"
|
||||||
|
name="tenantName "
|
||||||
|
>
|
||||||
|
<a-auto-complete
|
||||||
|
v-model:value="queryParams.tenantName"
|
||||||
|
:options="queryParams.tenantNameArr"
|
||||||
|
></a-auto-complete>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
|
<a-col :lg="6" :md="12" :xs="24">
|
||||||
|
<a-form-item>
|
||||||
|
<a-space :size="8">
|
||||||
|
<a-button type="primary" @click.prevent="fnGetList(1)">
|
||||||
|
<template #icon><SearchOutlined /></template>
|
||||||
|
{{ t('common.search') }}
|
||||||
|
</a-button>
|
||||||
|
<a-button type="default" @click.prevent="fnQueryReset">
|
||||||
|
<template #icon><ClearOutlined /></template>
|
||||||
|
{{ t('common.reset') }}
|
||||||
|
</a-button>
|
||||||
|
</a-space>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
<a-col :lg="8" :md="12" :xs="24">
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
:label="t('views.dashboard.cdr.time')"
|
:label="t('views.dashboard.cdr.time')"
|
||||||
@@ -473,20 +617,6 @@ onBeforeUnmount(() => {
|
|||||||
></a-range-picker>
|
></a-range-picker>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col :lg="6" :md="12" :xs="24">
|
|
||||||
<a-form-item>
|
|
||||||
<a-space :size="8">
|
|
||||||
<a-button type="primary" @click.prevent="fnGetList(1)">
|
|
||||||
<template #icon><SearchOutlined /></template>
|
|
||||||
{{ t('common.search') }}
|
|
||||||
</a-button>
|
|
||||||
<a-button type="default" @click.prevent="fnQueryReset">
|
|
||||||
<template #icon><ClearOutlined /></template>
|
|
||||||
{{ t('common.reset') }}
|
|
||||||
</a-button>
|
|
||||||
</a-space>
|
|
||||||
</a-form-item>
|
|
||||||
</a-col>
|
|
||||||
</a-row>
|
</a-row>
|
||||||
</a-form>
|
</a-form>
|
||||||
</a-card>
|
</a-card>
|
||||||
@@ -506,7 +636,11 @@ onBeforeUnmount(() => {
|
|||||||
cancel-text="No"
|
cancel-text="No"
|
||||||
@confirm="fnRealTime()"
|
@confirm="fnRealTime()"
|
||||||
>
|
>
|
||||||
<a-button type="primary" :danger="realTimeData">
|
<a-button
|
||||||
|
type="primary"
|
||||||
|
:danger="realTimeData"
|
||||||
|
v-roles:has="[TENANTADMIN_ROLE_KEY]"
|
||||||
|
>
|
||||||
<template #icon><FundOutlined /> </template>
|
<template #icon><FundOutlined /> </template>
|
||||||
{{
|
{{
|
||||||
!realTimeData
|
!realTimeData
|
||||||
@@ -522,6 +656,7 @@ onBeforeUnmount(() => {
|
|||||||
:disabled="tableState.selectedRowKeys.length <= 0"
|
:disabled="tableState.selectedRowKeys.length <= 0"
|
||||||
:loading="modalState.confirmLoading"
|
:loading="modalState.confirmLoading"
|
||||||
@click.prevent="fnRecordDelete('0')"
|
@click.prevent="fnRecordDelete('0')"
|
||||||
|
v-perms:has="['cdr:ne:remove']"
|
||||||
>
|
>
|
||||||
<template #icon><DeleteOutlined /></template>
|
<template #icon><DeleteOutlined /></template>
|
||||||
{{ t('common.deleteText') }}
|
{{ t('common.deleteText') }}
|
||||||
@@ -544,6 +679,7 @@ onBeforeUnmount(() => {
|
|||||||
:checked-children="t('common.switch.show')"
|
:checked-children="t('common.switch.show')"
|
||||||
:un-checked-children="t('common.switch.hide')"
|
:un-checked-children="t('common.switch.hide')"
|
||||||
size="small"
|
size="small"
|
||||||
|
:disabled="realTimeData"
|
||||||
/>
|
/>
|
||||||
</a-tooltip>
|
</a-tooltip>
|
||||||
<a-tooltip>
|
<a-tooltip>
|
||||||
@@ -552,6 +688,11 @@ onBeforeUnmount(() => {
|
|||||||
<template #icon><ReloadOutlined /></template>
|
<template #icon><ReloadOutlined /></template>
|
||||||
</a-button>
|
</a-button>
|
||||||
</a-tooltip>
|
</a-tooltip>
|
||||||
|
<TableColumnsDnd
|
||||||
|
cache-id="amfUeData"
|
||||||
|
:columns="tableColumns"
|
||||||
|
v-model:columns-dnd="tableColumnsDnd"
|
||||||
|
></TableColumnsDnd>
|
||||||
<a-tooltip>
|
<a-tooltip>
|
||||||
<template #title>{{ t('common.sizeText') }}</template>
|
<template #title>{{ t('common.sizeText') }}</template>
|
||||||
<a-dropdown trigger="click" placement="bottomRight">
|
<a-dropdown trigger="click" placement="bottomRight">
|
||||||
@@ -583,7 +724,7 @@ onBeforeUnmount(() => {
|
|||||||
<a-table
|
<a-table
|
||||||
class="table"
|
class="table"
|
||||||
row-key="id"
|
row-key="id"
|
||||||
:columns="tableColumns"
|
:columns="tableColumnsDnd"
|
||||||
:loading="tableState.loading"
|
:loading="tableState.loading"
|
||||||
:data-source="tableState.data"
|
:data-source="tableState.data"
|
||||||
:size="tableState.size"
|
:size="tableState.size"
|
||||||
@@ -604,7 +745,7 @@ onBeforeUnmount(() => {
|
|||||||
<span v-if="record.eventType === 'auth-result'">
|
<span v-if="record.eventType === 'auth-result'">
|
||||||
<DictTag
|
<DictTag
|
||||||
:options="dict.ueAauthCode"
|
:options="dict.ueAauthCode"
|
||||||
:value="record.eventJSON.authCode"
|
:value="record.eventJSON.result"
|
||||||
/>
|
/>
|
||||||
</span>
|
</span>
|
||||||
<span v-if="record.eventType === 'detach'">
|
<span v-if="record.eventType === 'detach'">
|
||||||
@@ -613,37 +754,29 @@ onBeforeUnmount(() => {
|
|||||||
<span v-if="record.eventType === 'cm-state'">
|
<span v-if="record.eventType === 'cm-state'">
|
||||||
<DictTag
|
<DictTag
|
||||||
:options="dict.ueEventCmState"
|
:options="dict.ueEventCmState"
|
||||||
:value="record.eventJSON.status"
|
:value="record.eventJSON.result"
|
||||||
/>
|
/>
|
||||||
</span>
|
</span>
|
||||||
</template>
|
</template>
|
||||||
<template v-if="column.key === 'time'">
|
|
||||||
<span
|
|
||||||
v-if="record.eventType === 'auth-result'"
|
|
||||||
:title="record.eventJSON.authTime"
|
|
||||||
>
|
|
||||||
{{ record.eventJSON.authTime }}
|
|
||||||
</span>
|
|
||||||
<span
|
|
||||||
v-if="record.eventType === 'detach'"
|
|
||||||
:title="record.eventJSON.detachTime"
|
|
||||||
>
|
|
||||||
{{ record.eventJSON.detachTime }}
|
|
||||||
</span>
|
|
||||||
<span
|
|
||||||
v-if="record.eventType === 'cm-state'"
|
|
||||||
:title="record.eventJSON.changeTime"
|
|
||||||
>
|
|
||||||
{{ record.eventJSON.changeTime }}
|
|
||||||
</span>
|
|
||||||
</template>
|
|
||||||
<template v-if="column.key === 'id'">
|
<template v-if="column.key === 'id'">
|
||||||
<a-space :size="8" align="center">
|
<a-space :size="8" align="center">
|
||||||
|
<a-tooltip>
|
||||||
|
<template #title>{{ t('common.copyText') }}</template>
|
||||||
|
<a-button
|
||||||
|
type="link"
|
||||||
|
@click.prevent="fnRecordCopy(record.eventJSON)"
|
||||||
|
>
|
||||||
|
<template #icon>
|
||||||
|
<CopyOutlined />
|
||||||
|
</template>
|
||||||
|
</a-button>
|
||||||
|
</a-tooltip>
|
||||||
<a-tooltip>
|
<a-tooltip>
|
||||||
<template #title>{{ t('common.deleteText') }}</template>
|
<template #title>{{ t('common.deleteText') }}</template>
|
||||||
<a-button
|
<a-button
|
||||||
type="link"
|
type="link"
|
||||||
@click.prevent="fnRecordDelete(record.id)"
|
@click.prevent="fnRecordDelete(record.id)"
|
||||||
|
v-perms:has="['cdr:ne:remove']"
|
||||||
>
|
>
|
||||||
<template #icon>
|
<template #icon>
|
||||||
<DeleteOutlined />
|
<DeleteOutlined />
|
||||||
@@ -654,65 +787,60 @@ onBeforeUnmount(() => {
|
|||||||
</template>
|
</template>
|
||||||
</template>
|
</template>
|
||||||
<template #expandedRowRender="{ record }">
|
<template #expandedRowRender="{ record }">
|
||||||
<div style="width: 46%; padding-left: 32px; padding-bottom: 16px">
|
<a-row :gutter="16">
|
||||||
<a-divider orientation="left">
|
<a-col :lg="8" :md="12" :xs="24" :offset="2">
|
||||||
{{ t('views.dashboard.ue.ueInfo') }}
|
<a-divider orientation="left">
|
||||||
</a-divider>
|
{{ t('views.dashboard.ue.ueInfo') }}
|
||||||
<div>
|
</a-divider>
|
||||||
<span>{{ t('views.ne.common.neName') }}: </span>
|
<div>
|
||||||
<span>{{ record.neName }}</span>
|
<span>{{ t('views.ne.common.neName') }}: </span>
|
||||||
</div>
|
<span>{{ record.neName }}</span>
|
||||||
<div>
|
</div>
|
||||||
<span>{{ t('views.ne.common.rmUid') }}: </span>
|
<div>
|
||||||
<span>{{ record.rmUID }}</span>
|
<span>{{ t('views.ne.common.rmUid') }}: </span>
|
||||||
</div>
|
<span>{{ record.rmUID }}</span>
|
||||||
<a-divider orientation="left">
|
</div>
|
||||||
{{ t('views.dashboard.ue.rowInfo') }}
|
</a-col>
|
||||||
</a-divider>
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<div>
|
<a-divider orientation="left">
|
||||||
<span>{{ t('views.dashboard.ue.time') }}: </span>
|
{{ t('views.dashboard.ue.rowInfo') }}
|
||||||
<span
|
</a-divider>
|
||||||
v-if="record.eventType === 'auth-result'"
|
<div>
|
||||||
:title="record.eventJSON.authTime"
|
<span>{{ t('views.dashboard.ue.time') }}: </span>
|
||||||
>
|
<template v-if="record.eventJSON?.time">
|
||||||
{{ record.eventJSON.authTime }}
|
{{ record.eventJSON.time }}
|
||||||
</span>
|
</template>
|
||||||
<span
|
<template v-else>
|
||||||
v-if="record.eventType === 'detach'"
|
{{ parseDateToStr(record.eventJSON.timestamp * 1000) }}
|
||||||
:title="record.eventJSON.detachTime"
|
</template>
|
||||||
>
|
</div>
|
||||||
{{ record.eventJSON.detachTime }}
|
<div>
|
||||||
</span>
|
<span>{{ t('views.dashboard.ue.eventType') }}: </span>
|
||||||
<span
|
|
||||||
v-if="record.eventType === 'cm-state'"
|
|
||||||
:title="record.eventJSON.changeTime"
|
|
||||||
>
|
|
||||||
{{ record.eventJSON.changeTime }}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.ue.eventType') }}: </span>
|
|
||||||
<DictTag :options="dict.ueEventType" :value="record.eventType" />
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.ue.result') }}: </span>
|
|
||||||
<span v-if="record.eventType === 'auth-result'">
|
|
||||||
<DictTag
|
<DictTag
|
||||||
:options="dict.ueAauthCode"
|
:options="dict.ueEventType"
|
||||||
:value="record.eventJSON.authCode"
|
:value="record.eventType"
|
||||||
/>
|
/>
|
||||||
</span>
|
</div>
|
||||||
<span v-if="record.eventType === 'detach'">
|
<div>
|
||||||
{{ t('views.dashboard.ue.resultOk') }}
|
<span>{{ t('views.dashboard.ue.result') }}: </span>
|
||||||
</span>
|
<span v-if="record.eventType === 'auth-result'">
|
||||||
<span v-if="record.eventType === 'cm-state'">
|
<DictTag
|
||||||
<DictTag
|
:options="dict.ueAauthCode"
|
||||||
:options="dict.ueEventCmState"
|
:value="record.eventJSON.result"
|
||||||
:value="record.eventJSON.status"
|
/>
|
||||||
/>
|
</span>
|
||||||
</span>
|
<span v-if="record.eventType === 'detach'">
|
||||||
</div>
|
{{ t('views.dashboard.ue.resultOk') }}
|
||||||
</div>
|
</span>
|
||||||
|
<span v-if="record.eventType === 'cm-state'">
|
||||||
|
<DictTag
|
||||||
|
:options="dict.ueEventCmState"
|
||||||
|
:value="record.eventJSON.result"
|
||||||
|
/>
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
</a-col>
|
||||||
|
</a-row>
|
||||||
</template>
|
</template>
|
||||||
</a-table>
|
</a-table>
|
||||||
</a-card>
|
</a-card>
|
||||||
|
|||||||
@@ -21,6 +21,11 @@ import { parseDateToStr, parseDuration } from '@/utils/date-utils';
|
|||||||
import { OptionsType, WS } from '@/plugins/ws-websocket';
|
import { OptionsType, WS } from '@/plugins/ws-websocket';
|
||||||
import saveAs from 'file-saver';
|
import saveAs from 'file-saver';
|
||||||
import PQueue from 'p-queue';
|
import PQueue from 'p-queue';
|
||||||
|
import { listTenant } from '@/api/system/tenant';
|
||||||
|
import { useClipboard } from '@vueuse/core';
|
||||||
|
import dayjs, { type Dayjs } from 'dayjs';
|
||||||
|
import { dayjsRanges } from '@/hooks/useRangePicker';
|
||||||
|
const { copy } = useClipboard({ legacy: true });
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const { getDict } = useDictStore();
|
const { getDict } = useDictStore();
|
||||||
const ws = new WS();
|
const ws = new WS();
|
||||||
@@ -32,31 +37,39 @@ let dict: {
|
|||||||
cdrSipCode: DictType[];
|
cdrSipCode: DictType[];
|
||||||
/**CDR 呼叫类型 */
|
/**CDR 呼叫类型 */
|
||||||
cdrCallType: DictType[];
|
cdrCallType: DictType[];
|
||||||
|
/**CDR SIP响应代码类别类型 */
|
||||||
|
cdrSipCodeCause: DictType[];
|
||||||
} = reactive({
|
} = reactive({
|
||||||
cdrSipCode: [],
|
cdrSipCode: [],
|
||||||
cdrCallType: [],
|
cdrCallType: [],
|
||||||
|
cdrSipCodeCause: [],
|
||||||
});
|
});
|
||||||
|
|
||||||
/**网元可选 */
|
/**网元可选 */
|
||||||
let neOtions = ref<Record<string, any>[]>([]);
|
let neOtions = ref<Record<string, any>[]>([]);
|
||||||
|
|
||||||
/**开始结束时间 */
|
/**开始结束时间 */
|
||||||
let queryRangePicker = ref<[string, string]>(['', '']);
|
let queryRangePicker = ref<[Dayjs, Dayjs] | undefined>([
|
||||||
|
dayjs().startOf('hour'),
|
||||||
|
dayjs().endOf('hour'),
|
||||||
|
]);
|
||||||
|
|
||||||
/**查询参数 */
|
/**查询参数 */
|
||||||
let queryParams = reactive({
|
let queryParams = reactive({
|
||||||
|
tenantNameArr: <Record<string, any>[]>[],
|
||||||
/**网元类型 */
|
/**网元类型 */
|
||||||
neType: 'IMS',
|
neType: 'IMS',
|
||||||
neId: '001',
|
neId: '001',
|
||||||
recordType: '',
|
recordType: '',
|
||||||
callerParty: '',
|
callerParty: '',
|
||||||
calledParty: '',
|
calledParty: '',
|
||||||
|
tenantName: '',
|
||||||
sortField: 'timestamp',
|
sortField: 'timestamp',
|
||||||
sortOrder: 'desc',
|
sortOrder: 'desc',
|
||||||
/**开始时间 */
|
/**开始时间 */
|
||||||
startTime: '',
|
startTime: undefined as undefined | number,
|
||||||
/**结束时间 */
|
/**结束时间 */
|
||||||
endTime: '',
|
endTime: undefined as undefined | number,
|
||||||
/**当前页数 */
|
/**当前页数 */
|
||||||
pageNum: 1,
|
pageNum: 1,
|
||||||
/**每页条数 */
|
/**每页条数 */
|
||||||
@@ -70,12 +83,13 @@ function fnQueryReset() {
|
|||||||
recordType: '',
|
recordType: '',
|
||||||
callerParty: '',
|
callerParty: '',
|
||||||
calledParty: '',
|
calledParty: '',
|
||||||
startTime: '',
|
tenantName: '',
|
||||||
endTime: '',
|
startTime: undefined,
|
||||||
|
endTime: undefined,
|
||||||
pageNum: 1,
|
pageNum: 1,
|
||||||
pageSize: 20,
|
pageSize: 20,
|
||||||
});
|
});
|
||||||
queryRangePicker.value = ['', ''];
|
queryRangePicker.value = [dayjs().startOf('hour'), dayjs().endOf('hour')];
|
||||||
tablePagination.current = 1;
|
tablePagination.current = 1;
|
||||||
tablePagination.pageSize = 20;
|
tablePagination.pageSize = 20;
|
||||||
fnGetList();
|
fnGetList();
|
||||||
@@ -116,12 +130,12 @@ let tableState: TabeStateType = reactive({
|
|||||||
|
|
||||||
/**表格字段列 */
|
/**表格字段列 */
|
||||||
let tableColumns: ColumnsType = [
|
let tableColumns: ColumnsType = [
|
||||||
{
|
// {
|
||||||
title: t('common.rowId'),
|
// title: t('common.rowId'),
|
||||||
dataIndex: 'id',
|
// dataIndex: 'id',
|
||||||
align: 'left',
|
// align: 'left',
|
||||||
width: 100,
|
// width: 100,
|
||||||
},
|
// },
|
||||||
{
|
{
|
||||||
title: t('views.dashboard.cdr.recordType'),
|
title: t('views.dashboard.cdr.recordType'),
|
||||||
dataIndex: 'cdrJSON',
|
dataIndex: 'cdrJSON',
|
||||||
@@ -161,13 +175,6 @@ let tableColumns: ColumnsType = [
|
|||||||
return cdrJSON.calledParty;
|
return cdrJSON.calledParty;
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
|
||||||
title: t('views.dashboard.cdr.result'),
|
|
||||||
dataIndex: 'cdrJSON',
|
|
||||||
key: 'cause',
|
|
||||||
align: 'left',
|
|
||||||
width: 150,
|
|
||||||
},
|
|
||||||
{
|
{
|
||||||
title: t('views.dashboard.cdr.duration'),
|
title: t('views.dashboard.cdr.duration'),
|
||||||
dataIndex: 'cdrJSON',
|
dataIndex: 'cdrJSON',
|
||||||
@@ -181,32 +188,77 @@ let tableColumns: ColumnsType = [
|
|||||||
: parseDuration(cdrJSON.callDuration);
|
: parseDuration(cdrJSON.callDuration);
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
title: t('views.dashboard.cdr.resultCode'),
|
||||||
|
dataIndex: 'cdrJSON',
|
||||||
|
key: 'code',
|
||||||
|
align: 'left',
|
||||||
|
width: 150,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: t('views.dashboard.cdr.resultCause'),
|
||||||
|
dataIndex: 'cdrJSON',
|
||||||
|
key: 'cause',
|
||||||
|
align: 'left',
|
||||||
|
width: 200,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: t('views.dashboard.cdr.mosAverage'),
|
||||||
|
dataIndex: 'cdrJSON',
|
||||||
|
key: 'mosAverage',
|
||||||
|
align: 'left',
|
||||||
|
width: 120,
|
||||||
|
customRender(opt) {
|
||||||
|
const cdrJSON = opt.value;
|
||||||
|
return cdrJSON.mosAverage;
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: t('views.dashboard.cdr.callConnectionTime'),
|
||||||
|
dataIndex: 'cdrJSON',
|
||||||
|
key: 'callConnectionTime',
|
||||||
|
align: 'left',
|
||||||
|
width: 200,
|
||||||
|
customRender(opt) {
|
||||||
|
const cdrJSON = opt.value;
|
||||||
|
return cdrJSON.callType === 'sms'
|
||||||
|
? '-'
|
||||||
|
: parseDuration(cdrJSON.callConnectionTime);
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
title: t('views.dashboard.cdr.seizureTime'),
|
title: t('views.dashboard.cdr.seizureTime'),
|
||||||
dataIndex: 'cdrJSON',
|
dataIndex: 'cdrJSON',
|
||||||
align: 'left',
|
align: 'left',
|
||||||
width: 200,
|
width: 250,
|
||||||
customRender(opt) {
|
customRender(opt) {
|
||||||
const cdrJSON = opt.value;
|
const cdrJSON = opt.value;
|
||||||
if (typeof cdrJSON.seizureTime === 'number') {
|
if (typeof cdrJSON.seizureTime === 'number') {
|
||||||
return parseDateToStr(+cdrJSON.seizureTime * 1000);
|
return parseDateToStr(+cdrJSON.seizureTime * 1000);
|
||||||
}
|
}
|
||||||
return cdrJSON.seizureTime;
|
return parseDateToStr(cdrJSON.seizureTime);
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
title: t('views.dashboard.cdr.releaseTime'),
|
title: t('views.dashboard.cdr.releaseTime'),
|
||||||
dataIndex: 'cdrJSON',
|
dataIndex: 'cdrJSON',
|
||||||
align: 'left',
|
align: 'left',
|
||||||
width: 200,
|
width: 250,
|
||||||
customRender(opt) {
|
customRender(opt) {
|
||||||
const cdrJSON = opt.value;
|
const cdrJSON = opt.value;
|
||||||
if (typeof cdrJSON.releaseTime === 'number') {
|
if (typeof cdrJSON.releaseTime === 'number') {
|
||||||
return parseDateToStr(+cdrJSON.releaseTime * 1000);
|
return parseDateToStr(+cdrJSON.releaseTime * 1000);
|
||||||
}
|
}
|
||||||
return cdrJSON.releaseTime;
|
return parseDateToStr(cdrJSON.releaseTime);
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
title: t('views.dashboard.cdr.tenantName'),
|
||||||
|
dataIndex: 'tenantName',
|
||||||
|
align: 'left',
|
||||||
|
key: 'tenantName',
|
||||||
|
width: 150,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
title: t('common.operate'),
|
title: t('common.operate'),
|
||||||
key: 'id',
|
key: 'id',
|
||||||
@@ -307,6 +359,18 @@ function fnRecordDelete(id: string) {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 复制CDR
|
||||||
|
* @param jsonStr JSON字符串
|
||||||
|
*/
|
||||||
|
function fnRecordCopy(jsonStr: string) {
|
||||||
|
if (!jsonStr) return;
|
||||||
|
const text = JSON.stringify(jsonStr, null, 2);
|
||||||
|
copy(text).then(() => {
|
||||||
|
message.success(t('common.copyOk'), 3);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
/**查询列表, pageNum初始页数 */
|
/**查询列表, pageNum初始页数 */
|
||||||
function fnGetList(pageNum?: number) {
|
function fnGetList(pageNum?: number) {
|
||||||
if (tableState.loading) return;
|
if (tableState.loading) return;
|
||||||
@@ -314,11 +378,17 @@ function fnGetList(pageNum?: number) {
|
|||||||
if (pageNum) {
|
if (pageNum) {
|
||||||
queryParams.pageNum = pageNum;
|
queryParams.pageNum = pageNum;
|
||||||
}
|
}
|
||||||
if (!queryRangePicker.value) {
|
// 时间范围
|
||||||
queryRangePicker.value = ['', ''];
|
if (
|
||||||
|
Array.isArray(queryRangePicker.value) &&
|
||||||
|
queryRangePicker.value.length > 0
|
||||||
|
) {
|
||||||
|
queryParams.startTime = queryRangePicker.value[0].valueOf();
|
||||||
|
queryParams.endTime = queryRangePicker.value[1].valueOf();
|
||||||
|
} else {
|
||||||
|
queryParams.startTime = undefined;
|
||||||
|
queryParams.endTime = undefined;
|
||||||
}
|
}
|
||||||
queryParams.startTime = queryRangePicker.value[0];
|
|
||||||
queryParams.endTime = queryRangePicker.value[1];
|
|
||||||
listIMSDataCDR(toRaw(queryParams)).then(res => {
|
listIMSDataCDR(toRaw(queryParams)).then(res => {
|
||||||
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.rows)) {
|
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.rows)) {
|
||||||
// 取消勾选
|
// 取消勾选
|
||||||
@@ -349,20 +419,25 @@ function fnGetList(pageNum?: number) {
|
|||||||
modalState.maxId = Number(res.rows[0].id);
|
modalState.maxId = Number(res.rows[0].id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
tableState.loading = false;
|
tableState.loading = false;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**列表导出 */
|
/**列表导出 */
|
||||||
function fnExportList() {
|
function fnExportList() {
|
||||||
if (modalState.confirmLoading) return;
|
if (modalState.confirmLoading || tablePagination.total === 0) return;
|
||||||
Modal.confirm({
|
Modal.confirm({
|
||||||
title: t('common.tipTitle'),
|
title: t('common.tipTitle'),
|
||||||
content: t('views.dashboard.cdr.exportTip'),
|
content: t('views.dashboard.cdr.exportTip'),
|
||||||
onOk() {
|
onOk() {
|
||||||
|
modalState.confirmLoading = true;
|
||||||
const hide = message.loading(t('common.loading'), 0);
|
const hide = message.loading(t('common.loading'), 0);
|
||||||
const querys = toRaw(queryParams);
|
const querys = toRaw(queryParams);
|
||||||
querys.pageSize = 10000;
|
querys.pageNum = 1;
|
||||||
|
querys.pageSize = tablePagination.total;
|
||||||
|
querys.startTime = Number(querys.startTime);
|
||||||
|
querys.endTime = Number(querys.endTime);
|
||||||
exportIMSDataCDR(querys)
|
exportIMSDataCDR(querys)
|
||||||
.then(res => {
|
.then(res => {
|
||||||
if (res.code === RESULT_CODE_SUCCESS) {
|
if (res.code === RESULT_CODE_SUCCESS) {
|
||||||
@@ -407,7 +482,9 @@ function fnRealTime() {
|
|||||||
subGroupID: `1005_${queryParams.neId}`,
|
subGroupID: `1005_${queryParams.neId}`,
|
||||||
},
|
},
|
||||||
onmessage: wsMessage,
|
onmessage: wsMessage,
|
||||||
onerror: wsError,
|
onerror: (ev: any) => {
|
||||||
|
console.error(ev);
|
||||||
|
},
|
||||||
};
|
};
|
||||||
ws.connect(options);
|
ws.connect(options);
|
||||||
} else {
|
} else {
|
||||||
@@ -417,12 +494,6 @@ function fnRealTime() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**接收数据后回调 */
|
|
||||||
function wsError(ev: any) {
|
|
||||||
// 接收数据后回调
|
|
||||||
console.error(ev);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**接收数据后回调 */
|
/**接收数据后回调 */
|
||||||
function wsMessage(res: Record<string, any>) {
|
function wsMessage(res: Record<string, any>) {
|
||||||
const { code, requestId, data } = res;
|
const { code, requestId, data } = res;
|
||||||
@@ -459,16 +530,21 @@ function wsMessage(res: Record<string, any>) {
|
|||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
// 初始字典数据
|
// 初始字典数据
|
||||||
Promise.allSettled([getDict('cdr_sip_code'), getDict('cdr_call_type')]).then(
|
Promise.allSettled([
|
||||||
resArr => {
|
getDict('cdr_sip_code'),
|
||||||
if (resArr[0].status === 'fulfilled') {
|
getDict('cdr_call_type'),
|
||||||
dict.cdrSipCode = resArr[0].value;
|
getDict('cdr_sip_code_cause'),
|
||||||
}
|
]).then(resArr => {
|
||||||
if (resArr[1].status === 'fulfilled') {
|
if (resArr[0].status === 'fulfilled') {
|
||||||
dict.cdrCallType = resArr[1].value;
|
dict.cdrSipCode = resArr[0].value;
|
||||||
}
|
|
||||||
}
|
}
|
||||||
);
|
if (resArr[1].status === 'fulfilled') {
|
||||||
|
dict.cdrCallType = resArr[1].value;
|
||||||
|
}
|
||||||
|
if (resArr[2].status === 'fulfilled') {
|
||||||
|
dict.cdrSipCodeCause = resArr[2].value;
|
||||||
|
}
|
||||||
|
});
|
||||||
// 获取网元网元列表
|
// 获取网元网元列表
|
||||||
useNeInfoStore()
|
useNeInfoStore()
|
||||||
.fnNelist()
|
.fnNelist()
|
||||||
@@ -497,6 +573,21 @@ onMounted(() => {
|
|||||||
// 获取列表数据
|
// 获取列表数据
|
||||||
fnGetList();
|
fnGetList();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
//查询租户
|
||||||
|
listTenant({ parentId: 0 }).then(res => {
|
||||||
|
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
|
||||||
|
queryParams.tenantNameArr = []; //上面置为空数组时会报错 故在此
|
||||||
|
res.data.forEach((item: any) => {
|
||||||
|
if (item.parentId === '0') {
|
||||||
|
queryParams.tenantNameArr.push({
|
||||||
|
value: item.tenantName,
|
||||||
|
label: item.tenantName,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
onBeforeUnmount(() => {
|
onBeforeUnmount(() => {
|
||||||
@@ -516,16 +607,17 @@ onBeforeUnmount(() => {
|
|||||||
<!-- 表格搜索栏 -->
|
<!-- 表格搜索栏 -->
|
||||||
<a-form :model="queryParams" name="queryParams" layout="horizontal">
|
<a-form :model="queryParams" name="queryParams" layout="horizontal">
|
||||||
<a-row :gutter="16">
|
<a-row :gutter="16">
|
||||||
<a-col :lg="6" :md="12" :xs="24">
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<a-form-item label="IMS" name="neId ">
|
<a-form-item label="IMS" name="neId ">
|
||||||
<a-select
|
<a-select
|
||||||
v-model:value="queryParams.neId"
|
v-model:value="queryParams.neId"
|
||||||
:options="neOtions"
|
:options="neOtions"
|
||||||
:placeholder="t('common.selectPlease')"
|
:placeholder="t('common.selectPlease')"
|
||||||
|
@change="fnQueryReset()"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col :lg="6" :md="12" :xs="24">
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
:label="t('views.dashboard.cdr.called')"
|
:label="t('views.dashboard.cdr.called')"
|
||||||
name="calledParty"
|
name="calledParty"
|
||||||
@@ -537,7 +629,7 @@ onBeforeUnmount(() => {
|
|||||||
></a-input>
|
></a-input>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col :lg="6" :md="12" :xs="24">
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
:label="t('views.dashboard.cdr.caller')"
|
:label="t('views.dashboard.cdr.caller')"
|
||||||
name="callerParty "
|
name="callerParty "
|
||||||
@@ -549,20 +641,6 @@ onBeforeUnmount(() => {
|
|||||||
></a-input>
|
></a-input>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col :lg="4" :md="12" :xs="24">
|
|
||||||
<a-form-item>
|
|
||||||
<a-space :size="8">
|
|
||||||
<a-button type="primary" @click.prevent="fnGetList(1)">
|
|
||||||
<template #icon><SearchOutlined /></template>
|
|
||||||
{{ t('common.search') }}
|
|
||||||
</a-button>
|
|
||||||
<a-button type="default" @click.prevent="fnQueryReset">
|
|
||||||
<template #icon><ClearOutlined /></template>
|
|
||||||
{{ t('common.reset') }}
|
|
||||||
</a-button>
|
|
||||||
</a-space>
|
|
||||||
</a-form-item>
|
|
||||||
</a-col>
|
|
||||||
<a-col :lg="8" :md="12" :xs="24">
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
:label="t('views.dashboard.cdr.recordType')"
|
:label="t('views.dashboard.cdr.recordType')"
|
||||||
@@ -584,15 +662,40 @@ onBeforeUnmount(() => {
|
|||||||
>
|
>
|
||||||
<a-range-picker
|
<a-range-picker
|
||||||
v-model:value="queryRangePicker"
|
v-model:value="queryRangePicker"
|
||||||
allow-clear
|
:presets="dayjsRanges()"
|
||||||
bordered
|
:bordered="true"
|
||||||
|
:allow-clear="false"
|
||||||
|
style="width: 100%"
|
||||||
:show-time="{ format: 'HH:mm:ss' }"
|
:show-time="{ format: 'HH:mm:ss' }"
|
||||||
format="YYYY-MM-DD HH:mm:ss"
|
format="YYYY-MM-DD HH:mm:ss"
|
||||||
value-format="x"
|
|
||||||
style="width: 100%"
|
|
||||||
></a-range-picker>
|
></a-range-picker>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
|
<a-form-item
|
||||||
|
:label="t('views.neUser.sub.tenantName')"
|
||||||
|
name="tenantName "
|
||||||
|
>
|
||||||
|
<a-auto-complete
|
||||||
|
v-model:value="queryParams.tenantName"
|
||||||
|
:options="queryParams.tenantNameArr"
|
||||||
|
></a-auto-complete>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
|
<a-col :lg="4" :md="12" :xs="24">
|
||||||
|
<a-form-item>
|
||||||
|
<a-space :size="8">
|
||||||
|
<a-button type="primary" @click.prevent="fnGetList(1)">
|
||||||
|
<template #icon><SearchOutlined /></template>
|
||||||
|
{{ t('common.search') }}
|
||||||
|
</a-button>
|
||||||
|
<a-button type="default" @click.prevent="fnQueryReset">
|
||||||
|
<template #icon><ClearOutlined /></template>
|
||||||
|
{{ t('common.reset') }}
|
||||||
|
</a-button>
|
||||||
|
</a-space>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
</a-row>
|
</a-row>
|
||||||
</a-form>
|
</a-form>
|
||||||
</a-card>
|
</a-card>
|
||||||
@@ -628,6 +731,7 @@ onBeforeUnmount(() => {
|
|||||||
:disabled="tableState.selectedRowKeys.length <= 0"
|
:disabled="tableState.selectedRowKeys.length <= 0"
|
||||||
:loading="modalState.confirmLoading"
|
:loading="modalState.confirmLoading"
|
||||||
@click.prevent="fnRecordDelete('0')"
|
@click.prevent="fnRecordDelete('0')"
|
||||||
|
v-perms:has="['cdr:ne:remove']"
|
||||||
>
|
>
|
||||||
<template #icon><DeleteOutlined /></template>
|
<template #icon><DeleteOutlined /></template>
|
||||||
{{ t('common.deleteText') }}
|
{{ t('common.deleteText') }}
|
||||||
@@ -695,7 +799,7 @@ onBeforeUnmount(() => {
|
|||||||
:data-source="tableState.data"
|
:data-source="tableState.data"
|
||||||
:size="tableState.size"
|
:size="tableState.size"
|
||||||
:pagination="tablePagination"
|
:pagination="tablePagination"
|
||||||
:scroll="{ x: tableColumns.length * 150, y: 'calc(100vh - 480px)' }"
|
:scroll="{ x: tableColumns.length * 160, y: 'calc(100vh - 480px)' }"
|
||||||
:row-selection="{
|
:row-selection="{
|
||||||
type: 'checkbox',
|
type: 'checkbox',
|
||||||
columnWidth: '48px',
|
columnWidth: '48px',
|
||||||
@@ -710,7 +814,7 @@ onBeforeUnmount(() => {
|
|||||||
:value="record.cdrJSON.callType"
|
:value="record.cdrJSON.callType"
|
||||||
/>
|
/>
|
||||||
</template>
|
</template>
|
||||||
<template v-if="column.key === 'cause'">
|
<template v-if="column.key === 'code'">
|
||||||
<span v-if="record.cdrJSON.callType !== 'sms'">
|
<span v-if="record.cdrJSON.callType !== 'sms'">
|
||||||
<DictTag
|
<DictTag
|
||||||
:options="dict.cdrSipCode"
|
:options="dict.cdrSipCode"
|
||||||
@@ -722,13 +826,35 @@ onBeforeUnmount(() => {
|
|||||||
{{ t('views.dashboard.cdr.resultOk') }}
|
{{ t('views.dashboard.cdr.resultOk') }}
|
||||||
</span>
|
</span>
|
||||||
</template>
|
</template>
|
||||||
|
<template v-if="column.key === 'cause'">
|
||||||
|
<span v-if="record.cdrJSON.callType !== 'sms'">
|
||||||
|
<DictTag
|
||||||
|
:options="dict.cdrSipCodeCause"
|
||||||
|
:value="record.cdrJSON.cause"
|
||||||
|
value-default="0"
|
||||||
|
/>
|
||||||
|
</span>
|
||||||
|
<span v-else> Call failure for other reason </span>
|
||||||
|
</template>
|
||||||
<template v-if="column.key === 'id'">
|
<template v-if="column.key === 'id'">
|
||||||
<a-space :size="8" align="center">
|
<a-space :size="8" align="center">
|
||||||
|
<a-tooltip>
|
||||||
|
<template #title>{{ t('common.copyText') }}</template>
|
||||||
|
<a-button
|
||||||
|
type="link"
|
||||||
|
@click.prevent="fnRecordCopy(record.cdrJSON)"
|
||||||
|
>
|
||||||
|
<template #icon>
|
||||||
|
<CopyOutlined />
|
||||||
|
</template>
|
||||||
|
</a-button>
|
||||||
|
</a-tooltip>
|
||||||
<a-tooltip>
|
<a-tooltip>
|
||||||
<template #title>{{ t('common.deleteText') }}</template>
|
<template #title>{{ t('common.deleteText') }}</template>
|
||||||
<a-button
|
<a-button
|
||||||
type="link"
|
type="link"
|
||||||
@click.prevent="fnRecordDelete(record.id)"
|
@click.prevent="fnRecordDelete(record.id)"
|
||||||
|
v-perms:has="['cdr:ne:remove']"
|
||||||
>
|
>
|
||||||
<template #icon>
|
<template #icon>
|
||||||
<DeleteOutlined />
|
<DeleteOutlined />
|
||||||
@@ -738,93 +864,6 @@ onBeforeUnmount(() => {
|
|||||||
</a-space>
|
</a-space>
|
||||||
</template>
|
</template>
|
||||||
</template>
|
</template>
|
||||||
<template #expandedRowRender="{ record }">
|
|
||||||
<a-row :gutter="16">
|
|
||||||
<a-col :lg="5" :md="12" :xs="24">
|
|
||||||
<a-divider orientation="left">
|
|
||||||
{{ t('views.dashboard.cdr.cdrInfo') }}
|
|
||||||
</a-divider>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.ne.common.neName') }}: </span>
|
|
||||||
<span>{{ record.neName }}</span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.ne.common.rmUid') }}: </span>
|
|
||||||
<span>{{ record.rmUID }}</span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.time') }}: </span>
|
|
||||||
<span>
|
|
||||||
{{
|
|
||||||
typeof record.cdrJSON.releaseTime === 'number'
|
|
||||||
? parseDateToStr(+record.cdrJSON.releaseTime * 1000)
|
|
||||||
: record.cdrJSON.releaseTime
|
|
||||||
}}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</a-col>
|
|
||||||
<a-col :lg="6" :md="12" :xs="24">
|
|
||||||
<a-divider orientation="left">
|
|
||||||
{{ t('views.dashboard.cdr.rowInfo') }}
|
|
||||||
</a-divider>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.type') }}: </span>
|
|
||||||
<DictTag
|
|
||||||
:options="dict.cdrCallType"
|
|
||||||
:value="record.cdrJSON.callType"
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.duration') }}: </span>
|
|
||||||
<span v-if="record.cdrJSON.callType !== 'sms'">
|
|
||||||
{{ parseDuration(record.cdrJSON.callDuration) }}
|
|
||||||
</span>
|
|
||||||
<span v-else> - </span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.caller') }}: </span>
|
|
||||||
<span>{{ record.cdrJSON.callerParty }}</span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.called') }}: </span>
|
|
||||||
<span>{{ record.cdrJSON.calledParty }}</span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.result') }}: </span>
|
|
||||||
<span v-if="record.cdrJSON.callType !== 'sms'">
|
|
||||||
<DictTag
|
|
||||||
:options="dict.cdrSipCode"
|
|
||||||
:value="record.cdrJSON.cause"
|
|
||||||
value-default="0"
|
|
||||||
/>
|
|
||||||
</span>
|
|
||||||
<span v-else>
|
|
||||||
{{ t('views.dashboard.cdr.resultOk') }}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.seizureTime') }}: </span>
|
|
||||||
<span>
|
|
||||||
{{
|
|
||||||
typeof record.cdrJSON.seizureTime === 'number'
|
|
||||||
? parseDateToStr(+record.cdrJSON.seizureTime * 1000)
|
|
||||||
: record.cdrJSON.seizureTime
|
|
||||||
}}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span>{{ t('views.dashboard.cdr.releaseTime') }}: </span>
|
|
||||||
<span>
|
|
||||||
{{
|
|
||||||
typeof record.cdrJSON.releaseTime === 'number'
|
|
||||||
? parseDateToStr(+record.cdrJSON.releaseTime * 1000)
|
|
||||||
: record.cdrJSON.releaseTime
|
|
||||||
}}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</a-col>
|
|
||||||
</a-row>
|
|
||||||
</template>
|
|
||||||
</a-table>
|
</a-table>
|
||||||
</a-card>
|
</a-card>
|
||||||
</PageContainer>
|
</PageContainer>
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
|
import dayjs, { Dayjs } from 'dayjs';
|
||||||
import { reactive, onMounted, toRaw, ref, onBeforeUnmount } from 'vue';
|
import { reactive, onMounted, toRaw, ref, onBeforeUnmount } from 'vue';
|
||||||
import { PageContainer } from 'antdv-pro-layout';
|
import { PageContainer } from 'antdv-pro-layout';
|
||||||
import { message, Modal } from 'ant-design-vue/es';
|
import { message, Modal } from 'ant-design-vue/es';
|
||||||
@@ -17,6 +18,9 @@ import { parseDateToStr } from '@/utils/date-utils';
|
|||||||
import { OptionsType, WS } from '@/plugins/ws-websocket';
|
import { OptionsType, WS } from '@/plugins/ws-websocket';
|
||||||
import saveAs from 'file-saver';
|
import saveAs from 'file-saver';
|
||||||
import PQueue from 'p-queue';
|
import PQueue from 'p-queue';
|
||||||
|
import { listTenant } from '@/api/system/tenant';
|
||||||
|
import { useClipboard } from '@vueuse/core';
|
||||||
|
const { copy } = useClipboard({ legacy: true });
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
const { getDict } = useDictStore();
|
const { getDict } = useDictStore();
|
||||||
const ws = new WS();
|
const ws = new WS();
|
||||||
@@ -40,21 +44,26 @@ let dict: {
|
|||||||
});
|
});
|
||||||
|
|
||||||
/**开始结束时间 */
|
/**开始结束时间 */
|
||||||
let queryRangePicker = ref<[string, string]>(['', '']);
|
let queryRangePicker = ref<[Dayjs, Dayjs] | undefined>([
|
||||||
|
dayjs().startOf('hour'),
|
||||||
|
dayjs().endOf('hour'),
|
||||||
|
]);
|
||||||
|
|
||||||
/**查询参数 */
|
/**查询参数 */
|
||||||
let queryParams = reactive({
|
let queryParams = reactive({
|
||||||
|
tenantNameArr: <Record<string, any>[]>[],
|
||||||
/**网元类型 */
|
/**网元类型 */
|
||||||
neType: 'MME',
|
neType: 'MME',
|
||||||
neId: '001',
|
neId: '001',
|
||||||
eventType: '',
|
eventType: '',
|
||||||
imsi: '',
|
imsi: '',
|
||||||
|
tenantName: '',
|
||||||
sortField: 'timestamp',
|
sortField: 'timestamp',
|
||||||
sortOrder: 'desc',
|
sortOrder: 'desc',
|
||||||
/**开始时间 */
|
/**开始时间 */
|
||||||
startTime: '',
|
startTime: undefined as undefined | number,
|
||||||
/**结束时间 */
|
/**结束时间 */
|
||||||
endTime: '',
|
endTime: undefined as undefined | number,
|
||||||
/**当前页数 */
|
/**当前页数 */
|
||||||
pageNum: 1,
|
pageNum: 1,
|
||||||
/**每页条数 */
|
/**每页条数 */
|
||||||
@@ -67,12 +76,13 @@ function fnQueryReset() {
|
|||||||
queryParams = Object.assign(queryParams, {
|
queryParams = Object.assign(queryParams, {
|
||||||
eventType: '',
|
eventType: '',
|
||||||
imsi: '',
|
imsi: '',
|
||||||
startTime: '',
|
tenantName: '',
|
||||||
endTime: '',
|
startTime: 0,
|
||||||
|
endTime: 0,
|
||||||
pageNum: 1,
|
pageNum: 1,
|
||||||
pageSize: 20,
|
pageSize: 20,
|
||||||
});
|
});
|
||||||
queryRangePicker.value = ['', ''];
|
queryRangePicker.value = [dayjs().startOf('hour'), dayjs().endOf('hour')];
|
||||||
tablePagination.current = 1;
|
tablePagination.current = 1;
|
||||||
tablePagination.pageSize = 20;
|
tablePagination.pageSize = 20;
|
||||||
fnGetList();
|
fnGetList();
|
||||||
@@ -113,12 +123,12 @@ let tableState: TabeStateType = reactive({
|
|||||||
|
|
||||||
/**表格字段列 */
|
/**表格字段列 */
|
||||||
let tableColumns: ColumnsType = [
|
let tableColumns: ColumnsType = [
|
||||||
{
|
// {
|
||||||
title: t('common.rowId'),
|
// title: t('common.rowId'),
|
||||||
dataIndex: 'id',
|
// dataIndex: 'id',
|
||||||
align: 'left',
|
// align: 'left',
|
||||||
width: 100,
|
// width: 100,
|
||||||
},
|
// },
|
||||||
{
|
{
|
||||||
title: 'IMSI',
|
title: 'IMSI',
|
||||||
dataIndex: 'eventJSON',
|
dataIndex: 'eventJSON',
|
||||||
@@ -147,12 +157,25 @@ let tableColumns: ColumnsType = [
|
|||||||
title: t('views.dashboard.ue.time'),
|
title: t('views.dashboard.ue.time'),
|
||||||
dataIndex: 'eventJSON',
|
dataIndex: 'eventJSON',
|
||||||
align: 'left',
|
align: 'left',
|
||||||
width: 150,
|
width: 250,
|
||||||
customRender(opt) {
|
customRender(opt) {
|
||||||
const cdrJSON = opt.value;
|
const record = opt.value;
|
||||||
return parseDateToStr(+cdrJSON.timestamp * 1000);
|
if (record?.time) {
|
||||||
|
return parseDateToStr(record.time);
|
||||||
|
}
|
||||||
|
if (record?.timestamp) {
|
||||||
|
return parseDateToStr(+record.timestamp * 1000);
|
||||||
|
}
|
||||||
|
return '';
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
title: t('views.dashboard.cdr.tenantName'),
|
||||||
|
dataIndex: 'tenantName',
|
||||||
|
align: 'center',
|
||||||
|
key: 'tenantName',
|
||||||
|
width: 150,
|
||||||
|
},
|
||||||
{
|
{
|
||||||
title: t('common.operate'),
|
title: t('common.operate'),
|
||||||
key: 'id',
|
key: 'id',
|
||||||
@@ -260,11 +283,19 @@ function fnGetList(pageNum?: number) {
|
|||||||
if (pageNum) {
|
if (pageNum) {
|
||||||
queryParams.pageNum = pageNum;
|
queryParams.pageNum = pageNum;
|
||||||
}
|
}
|
||||||
if (!queryRangePicker.value) {
|
|
||||||
queryRangePicker.value = ['', ''];
|
// 时间范围
|
||||||
|
if (
|
||||||
|
Array.isArray(queryRangePicker.value) &&
|
||||||
|
queryRangePicker.value.length > 0
|
||||||
|
) {
|
||||||
|
queryParams.startTime = queryRangePicker.value[0].valueOf();
|
||||||
|
queryParams.endTime = queryRangePicker.value[1].valueOf();
|
||||||
|
} else {
|
||||||
|
queryParams.startTime = undefined;
|
||||||
|
queryParams.endTime = undefined;
|
||||||
}
|
}
|
||||||
queryParams.startTime = queryRangePicker.value[0];
|
|
||||||
queryParams.endTime = queryRangePicker.value[1];
|
|
||||||
listMMEDataUE(toRaw(queryParams)).then(res => {
|
listMMEDataUE(toRaw(queryParams)).then(res => {
|
||||||
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.rows)) {
|
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.rows)) {
|
||||||
// 取消勾选
|
// 取消勾选
|
||||||
@@ -301,14 +332,18 @@ function fnGetList(pageNum?: number) {
|
|||||||
|
|
||||||
/**列表导出 */
|
/**列表导出 */
|
||||||
function fnExportList() {
|
function fnExportList() {
|
||||||
if (modalState.confirmLoading) return;
|
if (modalState.confirmLoading || tablePagination.total === 0) return;
|
||||||
Modal.confirm({
|
Modal.confirm({
|
||||||
title: t('common.tipTitle'),
|
title: t('common.tipTitle'),
|
||||||
content: t('views.dashboard.ue.exportTip'),
|
content: t('views.dashboard.ue.exportTip'),
|
||||||
onOk() {
|
onOk() {
|
||||||
|
modalState.confirmLoading = true;
|
||||||
const hide = message.loading(t('common.loading'), 0);
|
const hide = message.loading(t('common.loading'), 0);
|
||||||
const querys = toRaw(queryParams);
|
const querys = toRaw(queryParams);
|
||||||
querys.pageSize = 10000;
|
querys.pageNum = 1;
|
||||||
|
querys.pageSize = tablePagination.total;
|
||||||
|
querys.startTime = Number(querys.startTime);
|
||||||
|
querys.endTime = Number(querys.endTime);
|
||||||
exportMMEDataUE(querys)
|
exportMMEDataUE(querys)
|
||||||
.then(res => {
|
.then(res => {
|
||||||
if (res.code === RESULT_CODE_SUCCESS) {
|
if (res.code === RESULT_CODE_SUCCESS) {
|
||||||
@@ -332,6 +367,18 @@ function fnExportList() {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 复制CDR
|
||||||
|
* @param jsonStr JSON字符串
|
||||||
|
*/
|
||||||
|
function fnRecordCopy(jsonStr: string) {
|
||||||
|
if (!jsonStr) return;
|
||||||
|
const text = JSON.stringify(jsonStr, null, 2);
|
||||||
|
copy(text).then(() => {
|
||||||
|
message.success(t('common.copyOk'), 3);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
/**实时数据开关 */
|
/**实时数据开关 */
|
||||||
const realTimeData = ref<boolean>(false);
|
const realTimeData = ref<boolean>(false);
|
||||||
|
|
||||||
@@ -348,12 +395,14 @@ function fnRealTime() {
|
|||||||
params: {
|
params: {
|
||||||
/**订阅通道组
|
/**订阅通道组
|
||||||
*
|
*
|
||||||
* MME_UE会话事件(GroupID:1011)
|
* MME_UE会话事件(GroupID:1011_neId)
|
||||||
*/
|
*/
|
||||||
subGroupID: `1011_${queryParams.neId}`,
|
subGroupID: `1011_${queryParams.neId}`,
|
||||||
},
|
},
|
||||||
onmessage: wsMessage,
|
onmessage: wsMessage,
|
||||||
onerror: wsError,
|
onerror: (ev: any) => {
|
||||||
|
console.error(ev);
|
||||||
|
},
|
||||||
};
|
};
|
||||||
ws.connect(options);
|
ws.connect(options);
|
||||||
} else {
|
} else {
|
||||||
@@ -363,12 +412,6 @@ function fnRealTime() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**接收数据后回调 */
|
|
||||||
function wsError(ev: any) {
|
|
||||||
// 接收数据后回调
|
|
||||||
console.error(ev);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**接收数据后回调 */
|
/**接收数据后回调 */
|
||||||
function wsMessage(res: Record<string, any>) {
|
function wsMessage(res: Record<string, any>) {
|
||||||
const { code, requestId, data } = res;
|
const { code, requestId, data } = res;
|
||||||
@@ -415,7 +458,7 @@ onMounted(() => {
|
|||||||
dict.ueAauthCode = resArr[0].value;
|
dict.ueAauthCode = resArr[0].value;
|
||||||
}
|
}
|
||||||
if (resArr[1].status === 'fulfilled') {
|
if (resArr[1].status === 'fulfilled') {
|
||||||
const ueEventType: any[] = JSON.parse(JSON.stringify(resArr[1]));
|
const ueEventType: any[] = JSON.parse(JSON.stringify(resArr[1].value));
|
||||||
dict.ueEventType = ueEventType.map(item => {
|
dict.ueEventType = ueEventType.map(item => {
|
||||||
if (item.value === 'cm-state') {
|
if (item.value === 'cm-state') {
|
||||||
item.label = item.label.replace('CM', 'ECM');
|
item.label = item.label.replace('CM', 'ECM');
|
||||||
@@ -456,6 +499,21 @@ onMounted(() => {
|
|||||||
// 获取列表数据
|
// 获取列表数据
|
||||||
fnGetList();
|
fnGetList();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
//查询租户
|
||||||
|
listTenant({ parentId: 0 }).then(res => {
|
||||||
|
if (res.code === RESULT_CODE_SUCCESS && Array.isArray(res.data)) {
|
||||||
|
queryParams.tenantNameArr = []; //上面置为空数组时会报错 故在此
|
||||||
|
res.data.forEach((item: any) => {
|
||||||
|
if (item.parentId === '0') {
|
||||||
|
queryParams.tenantNameArr.push({
|
||||||
|
value: item.tenantName,
|
||||||
|
label: item.tenantName,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
onBeforeUnmount(() => {
|
onBeforeUnmount(() => {
|
||||||
@@ -481,6 +539,7 @@ onBeforeUnmount(() => {
|
|||||||
v-model:value="queryParams.neId"
|
v-model:value="queryParams.neId"
|
||||||
:options="neOtions"
|
:options="neOtions"
|
||||||
:placeholder="t('common.selectPlease')"
|
:placeholder="t('common.selectPlease')"
|
||||||
|
@change="fnGetList(1)"
|
||||||
/>
|
/>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
@@ -498,7 +557,7 @@ onBeforeUnmount(() => {
|
|||||||
></a-select>
|
></a-select>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col :lg="4" :md="12" :xs="24">
|
<a-col :lg="6" :md="12" :xs="24">
|
||||||
<a-form-item label="IMSI" name="imsi ">
|
<a-form-item label="IMSI" name="imsi ">
|
||||||
<a-input
|
<a-input
|
||||||
v-model:value="queryParams.imsi"
|
v-model:value="queryParams.imsi"
|
||||||
@@ -507,6 +566,31 @@ onBeforeUnmount(() => {
|
|||||||
></a-input>
|
></a-input>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
|
<a-col :lg="6" :md="12" :xs="24">
|
||||||
|
<a-form-item
|
||||||
|
:label="t('views.neUser.sub.tenantName')"
|
||||||
|
name="tenantName "
|
||||||
|
>
|
||||||
|
<a-auto-complete
|
||||||
|
v-model:value="queryParams.tenantName"
|
||||||
|
:options="queryParams.tenantNameArr"
|
||||||
|
></a-auto-complete>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
|
<a-col :lg="6" :md="12" :xs="24">
|
||||||
|
<a-form-item>
|
||||||
|
<a-space :size="8">
|
||||||
|
<a-button type="primary" @click.prevent="fnGetList(1)">
|
||||||
|
<template #icon><SearchOutlined /></template>
|
||||||
|
{{ t('common.search') }}
|
||||||
|
</a-button>
|
||||||
|
<a-button type="default" @click.prevent="fnQueryReset">
|
||||||
|
<template #icon><ClearOutlined /></template>
|
||||||
|
{{ t('common.reset') }}
|
||||||
|
</a-button>
|
||||||
|
</a-space>
|
||||||
|
</a-form-item>
|
||||||
|
</a-col>
|
||||||
<a-col :lg="8" :md="12" :xs="24">
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<a-form-item
|
<a-form-item
|
||||||
:label="t('views.dashboard.cdr.time')"
|
:label="t('views.dashboard.cdr.time')"
|
||||||
@@ -523,20 +607,6 @@ onBeforeUnmount(() => {
|
|||||||
></a-range-picker>
|
></a-range-picker>
|
||||||
</a-form-item>
|
</a-form-item>
|
||||||
</a-col>
|
</a-col>
|
||||||
<a-col :lg="6" :md="12" :xs="24">
|
|
||||||
<a-form-item>
|
|
||||||
<a-space :size="8">
|
|
||||||
<a-button type="primary" @click.prevent="fnGetList(1)">
|
|
||||||
<template #icon><SearchOutlined /></template>
|
|
||||||
{{ t('common.search') }}
|
|
||||||
</a-button>
|
|
||||||
<a-button type="default" @click.prevent="fnQueryReset">
|
|
||||||
<template #icon><ClearOutlined /></template>
|
|
||||||
{{ t('common.reset') }}
|
|
||||||
</a-button>
|
|
||||||
</a-space>
|
|
||||||
</a-form-item>
|
|
||||||
</a-col>
|
|
||||||
</a-row>
|
</a-row>
|
||||||
</a-form>
|
</a-form>
|
||||||
</a-card>
|
</a-card>
|
||||||
@@ -572,6 +642,7 @@ onBeforeUnmount(() => {
|
|||||||
:disabled="tableState.selectedRowKeys.length <= 0"
|
:disabled="tableState.selectedRowKeys.length <= 0"
|
||||||
:loading="modalState.confirmLoading"
|
:loading="modalState.confirmLoading"
|
||||||
@click.prevent="fnRecordDelete('0')"
|
@click.prevent="fnRecordDelete('0')"
|
||||||
|
v-perms:has="['cdr:ne:remove']"
|
||||||
>
|
>
|
||||||
<template #icon><DeleteOutlined /></template>
|
<template #icon><DeleteOutlined /></template>
|
||||||
{{ t('common.deleteText') }}
|
{{ t('common.deleteText') }}
|
||||||
@@ -670,11 +741,23 @@ onBeforeUnmount(() => {
|
|||||||
</template>
|
</template>
|
||||||
<template v-if="column.key === 'id'">
|
<template v-if="column.key === 'id'">
|
||||||
<a-space :size="8" align="center">
|
<a-space :size="8" align="center">
|
||||||
|
<a-tooltip>
|
||||||
|
<template #title>{{ t('common.copyText') }}</template>
|
||||||
|
<a-button
|
||||||
|
type="link"
|
||||||
|
@click.prevent="fnRecordCopy(record.eventJSON)"
|
||||||
|
>
|
||||||
|
<template #icon>
|
||||||
|
<CopyOutlined />
|
||||||
|
</template>
|
||||||
|
</a-button>
|
||||||
|
</a-tooltip>
|
||||||
<a-tooltip>
|
<a-tooltip>
|
||||||
<template #title>{{ t('common.deleteText') }}</template>
|
<template #title>{{ t('common.deleteText') }}</template>
|
||||||
<a-button
|
<a-button
|
||||||
type="link"
|
type="link"
|
||||||
@click.prevent="fnRecordDelete(record.id)"
|
@click.prevent="fnRecordDelete(record.id)"
|
||||||
|
v-perms:has="['cdr:ne:remove']"
|
||||||
>
|
>
|
||||||
<template #icon>
|
<template #icon>
|
||||||
<DeleteOutlined />
|
<DeleteOutlined />
|
||||||
@@ -685,48 +768,60 @@ onBeforeUnmount(() => {
|
|||||||
</template>
|
</template>
|
||||||
</template>
|
</template>
|
||||||
<template #expandedRowRender="{ record }">
|
<template #expandedRowRender="{ record }">
|
||||||
<div style="width: 46%; padding-left: 32px; padding-bottom: 16px">
|
<a-row :gutter="16">
|
||||||
<a-divider orientation="left">
|
<a-col :lg="8" :md="12" :xs="24" :offset="2">
|
||||||
{{ t('views.dashboard.ue.ueInfo') }}
|
<a-divider orientation="left">
|
||||||
</a-divider>
|
{{ t('views.dashboard.ue.ueInfo') }}
|
||||||
<div>
|
</a-divider>
|
||||||
<span>{{ t('views.ne.common.neName') }}: </span>
|
<div>
|
||||||
<span>{{ record.neName }}</span>
|
<span>{{ t('views.ne.common.neName') }}: </span>
|
||||||
</div>
|
<span>{{ record.neName }}</span>
|
||||||
<div>
|
</div>
|
||||||
<span>{{ t('views.ne.common.rmUid') }}: </span>
|
<div>
|
||||||
<span>{{ record.rmUID }}</span>
|
<span>{{ t('views.ne.common.rmUid') }}: </span>
|
||||||
</div>
|
<span>{{ record.rmUID }}</span>
|
||||||
<a-divider orientation="left">
|
</div>
|
||||||
{{ t('views.dashboard.ue.rowInfo') }}
|
</a-col>
|
||||||
</a-divider>
|
<a-col :lg="8" :md="12" :xs="24">
|
||||||
<div>
|
<a-divider orientation="left">
|
||||||
<span>{{ t('views.dashboard.ue.time') }}: </span>
|
{{ t('views.dashboard.ue.rowInfo') }}
|
||||||
{{ parseDateToStr(record.eventJSON.timestamp * 1000) }}
|
</a-divider>
|
||||||
</div>
|
<div>
|
||||||
<div>
|
<span>{{ t('views.dashboard.ue.time') }}: </span>
|
||||||
<span>{{ t('views.dashboard.ue.eventType') }}: </span>
|
<template v-if="record.eventJSON?.time">
|
||||||
<DictTag :options="dict.ueEventType" :value="record.eventType" />
|
{{ record.eventJSON.time }}
|
||||||
</div>
|
</template>
|
||||||
<div>
|
<template v-else>
|
||||||
<span>{{ t('views.dashboard.ue.result') }}: </span>
|
{{ parseDateToStr(record.eventJSON.timestamp * 1000) }}
|
||||||
<span v-if="record.eventType === 'auth-result'">
|
</template>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<span>{{ t('views.dashboard.ue.eventType') }}: </span>
|
||||||
<DictTag
|
<DictTag
|
||||||
:options="dict.ueAauthCode"
|
:options="dict.ueEventType"
|
||||||
:value="record.eventJSON.result"
|
:value="record.eventType"
|
||||||
/>
|
/>
|
||||||
</span>
|
</div>
|
||||||
<span v-if="record.eventType === 'detach'">
|
<div>
|
||||||
{{ t('views.dashboard.ue.resultOk') }}
|
<span>{{ t('views.dashboard.ue.result') }}: </span>
|
||||||
</span>
|
<span v-if="record.eventType === 'auth-result'">
|
||||||
<span v-if="record.eventType === 'cm-state'">
|
<DictTag
|
||||||
<DictTag
|
:options="dict.ueAauthCode"
|
||||||
:options="dict.ueEventCmState"
|
:value="record.eventJSON.result"
|
||||||
:value="record.eventJSON.result"
|
/>
|
||||||
/>
|
</span>
|
||||||
</span>
|
<span v-if="record.eventType === 'detach'">
|
||||||
</div>
|
{{ t('views.dashboard.ue.resultOk') }}
|
||||||
</div>
|
</span>
|
||||||
|
<span v-if="record.eventType === 'cm-state'">
|
||||||
|
<DictTag
|
||||||
|
:options="dict.ueEventCmState"
|
||||||
|
:value="record.eventJSON.result"
|
||||||
|
/>
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
</a-col>
|
||||||
|
</a-row>
|
||||||
</template>
|
</template>
|
||||||
</a-table>
|
</a-table>
|
||||||
</a-card>
|
</a-card>
|
||||||
|
|||||||
@@ -236,8 +236,11 @@ function handleRanderChart(
|
|||||||
}
|
}
|
||||||
|
|
||||||
function fnChangeData(data: any[], itemID: string) {
|
function fnChangeData(data: any[], itemID: string) {
|
||||||
let info = data.find((item: any) => item.id === itemID);
|
const neType=itemID.split('_')[0];
|
||||||
if (!info || !info.neState.online) return;
|
const neID=itemID.split('_')[1];
|
||||||
|
let info = data.find((item: any) => item.id === neType);
|
||||||
|
|
||||||
|
if (!info || !info.neStateMap[neID]?.online) return;
|
||||||
// if (!info.neState.online) {
|
// if (!info.neState.online) {
|
||||||
// info = data.find((item: any) => item.id === itemID);
|
// info = data.find((item: any) => item.id === itemID);
|
||||||
// graphNodeClickID.value = itemID;
|
// graphNodeClickID.value = itemID;
|
||||||
@@ -249,16 +252,16 @@ function fnChangeData(data: any[], itemID: string) {
|
|||||||
// console.log(info.neState.disk);
|
// console.log(info.neState.disk);
|
||||||
let sysCpuUsage = 0;
|
let sysCpuUsage = 0;
|
||||||
let nfCpuUsage = 0;
|
let nfCpuUsage = 0;
|
||||||
if (info.neState.cpu) {
|
if (info.neStateMap[neID].cpu) {
|
||||||
nfCpuUsage = info.neState.cpu.nfCpuUsage;
|
nfCpuUsage = info.neStateMap[neID].cpu.nfCpuUsage;
|
||||||
const nfCpu = +(info.neState.cpu.nfCpuUsage / 100);
|
const nfCpu = +(info.neStateMap[neID].cpu.nfCpuUsage / 100);
|
||||||
nfCpuUsage = +nfCpu.toFixed(2);
|
nfCpuUsage = +nfCpu.toFixed(2);
|
||||||
if (nfCpuUsage > 100) {
|
if (nfCpuUsage > 100) {
|
||||||
nfCpuUsage = 100;
|
nfCpuUsage = 100;
|
||||||
}
|
}
|
||||||
|
|
||||||
sysCpuUsage = info.neState.cpu.sysCpuUsage;
|
sysCpuUsage = info.neStateMap[neID].cpu.sysCpuUsage;
|
||||||
let sysCpu = +(info.neState.cpu.sysCpuUsage / 100);
|
let sysCpu = +(info.neStateMap[neID].cpu.sysCpuUsage / 100);
|
||||||
sysCpuUsage = +sysCpu.toFixed(2);
|
sysCpuUsage = +sysCpu.toFixed(2);
|
||||||
if (sysCpuUsage > 100) {
|
if (sysCpuUsage > 100) {
|
||||||
sysCpuUsage = 100;
|
sysCpuUsage = 100;
|
||||||
@@ -266,8 +269,8 @@ function fnChangeData(data: any[], itemID: string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let sysMemUsage = 0;
|
let sysMemUsage = 0;
|
||||||
if (info.neState.mem) {
|
if (info.neStateMap[neID].mem) {
|
||||||
const men = info.neState.mem.sysMemUsage;
|
const men = info.neStateMap[neID].mem.sysMemUsage;
|
||||||
sysMemUsage = +(men / 100).toFixed(2);
|
sysMemUsage = +(men / 100).toFixed(2);
|
||||||
if (sysMemUsage > 100) {
|
if (sysMemUsage > 100) {
|
||||||
sysMemUsage = 100;
|
sysMemUsage = 100;
|
||||||
@@ -275,8 +278,8 @@ function fnChangeData(data: any[], itemID: string) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let sysDiskUsage = 0;
|
let sysDiskUsage = 0;
|
||||||
if (info.neState.disk && Array.isArray(info.neState.disk.partitionInfo)) {
|
if (info.neStateMap[neID].disk && Array.isArray(info.neStateMap[neID].disk.partitionInfo)) {
|
||||||
let disks: any[] = info.neState.disk.partitionInfo;
|
let disks: any[] = info.neStateMap[neID].disk.partitionInfo;
|
||||||
disks = disks.sort((a, b) => +b.used - +a.used);
|
disks = disks.sort((a, b) => +b.used - +a.used);
|
||||||
if (disks.length > 0) {
|
if (disks.length > 0) {
|
||||||
const { total, used } = disks[0];
|
const { total, used } = disks[0];
|
||||||
|
|||||||
@@ -22,18 +22,25 @@ const graphG6Dom = ref<HTMLElement | undefined>(undefined);
|
|||||||
|
|
||||||
/**图节点展示 */
|
/**图节点展示 */
|
||||||
const graphNodeTooltip = new Tooltip({
|
const graphNodeTooltip = new Tooltip({
|
||||||
offsetX: 20,
|
offsetX: 10,
|
||||||
offsetY: 20,
|
offsetY: 20,
|
||||||
getContent(evt) {
|
getContent(evt) {
|
||||||
if (!evt) return t('views.monitor.topologyBuild.graphNotInfo');
|
if (!evt) return t('views.monitor.topologyBuild.graphNotInfo');
|
||||||
const { id, label, neState }: any = evt.item?.getModel();
|
const { id, label, neState, neInfoList, neStateMap }: any = evt.item?.getModel();
|
||||||
|
//console.log(neInfoList,neState,neInfoList);
|
||||||
if (notNeNodes.includes(id)) {
|
if (notNeNodes.includes(id)) {
|
||||||
return `<div><span>${label || id}</span></div>`;
|
return `<div><span>${label || id}</span></div>`;
|
||||||
}
|
}
|
||||||
if (!neState) {
|
if (!neState) {
|
||||||
return `<div><span>${label || id}</span></div>`;
|
return `<div><span>${label || id}</span></div>`;
|
||||||
}
|
}
|
||||||
return `
|
|
||||||
|
// 获取同类型网元列表
|
||||||
|
const sameTypeNes = neInfoList || [];
|
||||||
|
|
||||||
|
// 如果没有网元或只有一个网元,显示原来的信息
|
||||||
|
if (sameTypeNes.length <= 1) {
|
||||||
|
return `
|
||||||
<div
|
<div
|
||||||
style="
|
style="
|
||||||
display: flex;
|
display: flex;
|
||||||
@@ -56,7 +63,7 @@ const graphNodeTooltip = new Tooltip({
|
|||||||
<div><strong>${t('views.monitor.topology.name')}:</strong><span>
|
<div><strong>${t('views.monitor.topology.name')}:</strong><span>
|
||||||
${neState.neName ?? '--'}
|
${neState.neName ?? '--'}
|
||||||
</span></div>
|
</span></div>
|
||||||
<div><strong>IP:</strong><span>${neState.neIP}</span></div>
|
<div><strong>IP:</strong><span>${neState.neIP ?? '--'}</span></div>
|
||||||
<div><strong>${t('views.monitor.topology.version')}:</strong><span>
|
<div><strong>${t('views.monitor.topology.version')}:</strong><span>
|
||||||
${neState.version ?? '--'}
|
${neState.version ?? '--'}
|
||||||
</span></div>
|
</span></div>
|
||||||
@@ -68,21 +75,68 @@ const graphNodeTooltip = new Tooltip({
|
|||||||
</span></div>
|
</span></div>
|
||||||
</div>
|
</div>
|
||||||
`;
|
`;
|
||||||
|
}
|
||||||
|
|
||||||
|
// 如果有多个网元,聚合显示
|
||||||
|
let content = `
|
||||||
|
<div
|
||||||
|
style="
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
width: 300px;
|
||||||
|
"
|
||||||
|
>
|
||||||
|
<div><strong>${t('views.monitor.topology.state')}:</strong><span>
|
||||||
|
${
|
||||||
|
neState.online
|
||||||
|
? t('views.monitor.topology.normalcy')
|
||||||
|
: t('views.monitor.topology.exceptions')
|
||||||
|
}
|
||||||
|
</span></div>
|
||||||
|
<div><strong>${t('views.monitor.topology.refreshTime')}:</strong><span>
|
||||||
|
${neState.refreshTime ?? '--'}
|
||||||
|
</span></div>
|
||||||
|
<div>========================</div>`;
|
||||||
|
|
||||||
|
// 为每个同类型网元添加信息
|
||||||
|
sameTypeNes.forEach((ne: any, index: number) => {
|
||||||
|
// 获取该网元的状态信息
|
||||||
|
const neStateInfo = neStateMap?.[ne.neId] ||
|
||||||
|
(ne.neId === neState.neId ? neState : {});
|
||||||
|
|
||||||
|
content += `
|
||||||
|
<div style="margin-top: 8px;"><strong>${t('views.monitor.topology.name')}:${ne.neName || id + '_' + ne.neId}</strong></div>
|
||||||
|
<div><strong>ID:</strong><span>${ne.neId || '--'}</span></div>
|
||||||
|
<div><strong>IP:</strong><span>${neStateInfo.neIP || ne.neIP || '--'}</span></div>
|
||||||
|
<div><strong>${t('views.monitor.topology.version')}:</strong><span>
|
||||||
|
${neStateInfo.version || ne.version || '--'}
|
||||||
|
</span></div>
|
||||||
|
<div><strong>${t('views.monitor.topology.serialNum')}:</strong><span>
|
||||||
|
${neStateInfo.sn || ne.sn || '--'}
|
||||||
|
</span></div>
|
||||||
|
<div><strong>${t('views.monitor.topology.expiryDate')}:</strong><span>
|
||||||
|
${neStateInfo.expire || ne.expire || '--'}
|
||||||
|
</span></div>
|
||||||
|
<div><strong>${t('views.monitor.topology.state')}:</strong><span>
|
||||||
|
${
|
||||||
|
neStateInfo.online !== undefined
|
||||||
|
? (neStateInfo.online
|
||||||
|
? t('views.monitor.topology.normalcy')
|
||||||
|
: t('views.monitor.topology.exceptions'))
|
||||||
|
: 'undefined'
|
||||||
|
}
|
||||||
|
</span></div>
|
||||||
|
${index < sameTypeNes.length - 1 ? '<div>------------------------</div>' : ''}
|
||||||
|
`;
|
||||||
|
});
|
||||||
|
|
||||||
|
content += '</div>';
|
||||||
|
return content;
|
||||||
},
|
},
|
||||||
itemTypes: ['node'],
|
itemTypes: ['node'],
|
||||||
});
|
});
|
||||||
|
|
||||||
/**图绑定事件 */
|
|
||||||
function fnGraphEvent(graph: Graph) {
|
|
||||||
// 节点点击
|
|
||||||
graph.on('node:click', evt => {
|
|
||||||
// 获得鼠标当前目标节点
|
|
||||||
const node = evt.item?.getModel();
|
|
||||||
if (node && node.id && !notNeNodes.includes(node.id)) {
|
|
||||||
graphNodeClickID.value = node.id;
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
/**图数据渲染 */
|
/**图数据渲染 */
|
||||||
function handleRanderGraph(
|
function handleRanderGraph(
|
||||||
@@ -104,7 +158,7 @@ function handleRanderGraph(
|
|||||||
fitViewPadding: [20],
|
fitViewPadding: [20],
|
||||||
autoPaint: true,
|
autoPaint: true,
|
||||||
modes: {
|
modes: {
|
||||||
default: ['drag-canvas', 'zoom-canvas'],
|
// default: ['drag-canvas', 'zoom-canvas'],
|
||||||
},
|
},
|
||||||
groupByTypes: false,
|
groupByTypes: false,
|
||||||
nodeStateStyles: {
|
nodeStateStyles: {
|
||||||
@@ -122,7 +176,6 @@ function handleRanderGraph(
|
|||||||
graph.data(data);
|
graph.data(data);
|
||||||
graph.render();
|
graph.render();
|
||||||
|
|
||||||
fnGraphEvent(graph);
|
|
||||||
|
|
||||||
graphG6.value = graph;
|
graphG6.value = graph;
|
||||||
|
|
||||||
@@ -150,14 +203,14 @@ function handleRanderGraph(
|
|||||||
* 获取图组数据渲染到画布
|
* 获取图组数据渲染到画布
|
||||||
* @param reload 是否重载数据
|
* @param reload 是否重载数据
|
||||||
*/
|
*/
|
||||||
function fnGraphDataLoad(reload: boolean = false) {
|
function fnGraphDataLoad(reload: boolean = false) {
|
||||||
Promise.all([
|
Promise.all([
|
||||||
getGraphData(graphState.group),
|
getGraphData(graphState.group),
|
||||||
listAllNeInfo({
|
listAllNeInfo({
|
||||||
bandStatus: false,
|
bandStatus: false,
|
||||||
}),
|
}),
|
||||||
])
|
])
|
||||||
.then(resArr => {
|
.then(resArr => {
|
||||||
const graphRes = resArr[0];
|
const graphRes = resArr[0];
|
||||||
const neRes = resArr[1];
|
const neRes = resArr[1];
|
||||||
if (
|
if (
|
||||||
@@ -183,27 +236,45 @@ function fnGraphDataLoad(reload: boolean = false) {
|
|||||||
if (!res) return;
|
if (!res) return;
|
||||||
const { combos, edges, nodes } = res.graphData;
|
const { combos, edges, nodes } = res.graphData;
|
||||||
|
|
||||||
|
// 按网元类型分组
|
||||||
|
const neTypeMap = new Map();
|
||||||
|
res.neList.forEach(ne => {
|
||||||
|
if (!ne.neType) return;
|
||||||
|
if (!neTypeMap.has(ne.neType)) {
|
||||||
|
neTypeMap.set(ne.neType, []);
|
||||||
|
}
|
||||||
|
neTypeMap.get(ne.neType).push(ne);
|
||||||
|
});
|
||||||
|
|
||||||
// 节点过滤
|
// 节点过滤
|
||||||
const nf: Record<string, any>[] = nodes.filter(
|
const nf: Record<string, any>[] = nodes.filter(
|
||||||
(node: Record<string, any>) => {
|
(node: Record<string, any>) => {
|
||||||
Reflect.set(node, 'neState', { online: false });
|
Reflect.set(node, 'neState', { online: false });
|
||||||
|
Reflect.set(node, 'neStateMap', {}); // 初始化状态映射
|
||||||
|
|
||||||
// 图片路径处理
|
// 图片路径处理
|
||||||
if (node.img) node.img = parseBasePath(node.img);
|
if (node.img) node.img = parseBasePath(node.img);
|
||||||
if (node.icon.show && node.icon?.img) {
|
if (node.icon.show && node.icon?.img){
|
||||||
node.icon.img = parseBasePath(node.icon.img);
|
node.icon.img = parseBasePath(node.icon.img);
|
||||||
}
|
}
|
||||||
|
|
||||||
// 遍历是否有网元数据
|
// 遍历是否有网元数据
|
||||||
const nodeID: string = node.id;
|
const nodeID: string = node.id;
|
||||||
const hasNe = res.neList.some(ne => {
|
|
||||||
Reflect.set(node, 'neInfo', ne.neType === nodeID ? ne : {});
|
// 处理非网元节点
|
||||||
return ne.neType === nodeID;
|
|
||||||
});
|
|
||||||
if (hasNe) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (notNeNodes.includes(nodeID)) {
|
if (notNeNodes.includes(nodeID)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
//(neTypeMap.get(nodeID),nodeID,node.neState)
|
||||||
|
// 处理网元节点
|
||||||
|
if (neTypeMap.has(nodeID)) {
|
||||||
|
// all NeInfo
|
||||||
|
Reflect.set(node, 'neInfoList', neTypeMap.get(nodeID));
|
||||||
|
|
||||||
|
Reflect.set(node, 'neInfo', neTypeMap.get(nodeID)[0] || {});
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
@@ -215,7 +286,6 @@ function fnGraphDataLoad(reload: boolean = false) {
|
|||||||
const edgeTarget: string = edge.target;
|
const edgeTarget: string = edge.target;
|
||||||
const hasNeS = nf.some(n => n.id === edgeSource);
|
const hasNeS = nf.some(n => n.id === edgeSource);
|
||||||
const hasNeT = nf.some(n => n.id === edgeTarget);
|
const hasNeT = nf.some(n => n.id === edgeTarget);
|
||||||
// console.log(hasNeS, edgeSource, hasNeT, edgeTarget);
|
|
||||||
if (hasNeS && hasNeT) {
|
if (hasNeS && hasNeT) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -15,9 +15,9 @@ import { UniversalTransition } from 'echarts/features';
|
|||||||
import { CanvasRenderer } from 'echarts/renderers';
|
import { CanvasRenderer } from 'echarts/renderers';
|
||||||
import { markRaw } from 'vue';
|
import { markRaw } from 'vue';
|
||||||
import useI18n from '@/hooks/useI18n';
|
import useI18n from '@/hooks/useI18n';
|
||||||
import { parseDateToStr } from '@/utils/date-utils';
|
|
||||||
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
import { RESULT_CODE_SUCCESS } from '@/constants/result-constants';
|
||||||
import { upfFlowData, upfFlowParse } from '../../hooks/useUPFTotalFlow';
|
import { upfFlowData, upfFlowParse } from '../../hooks/useUPFTotalFlow';
|
||||||
|
import { upfWhoId } from '../../hooks/useWS';
|
||||||
|
|
||||||
const { t } = useI18n();
|
const { t } = useI18n();
|
||||||
|
|
||||||
@@ -151,7 +151,7 @@ function handleRanderChart() {
|
|||||||
top: '14%',
|
top: '14%',
|
||||||
left: '4%',
|
left: '4%',
|
||||||
right: '4%',
|
right: '4%',
|
||||||
bottom: '12%',
|
bottom: '16%',
|
||||||
containLabel: true,
|
containLabel: true,
|
||||||
},
|
},
|
||||||
xAxis: {
|
xAxis: {
|
||||||
@@ -160,7 +160,7 @@ function handleRanderChart() {
|
|||||||
data: lineXTime,
|
data: lineXTime,
|
||||||
axisLabel: {
|
axisLabel: {
|
||||||
formatter: function (params: any) {
|
formatter: function (params: any) {
|
||||||
return params.split(' ')[1];
|
return params;
|
||||||
},
|
},
|
||||||
fontSize: 14,
|
fontSize: 14,
|
||||||
},
|
},
|
||||||
@@ -208,9 +208,10 @@ function fnGetInitData() {
|
|||||||
|
|
||||||
listKPIData({
|
listKPIData({
|
||||||
neType: 'UPF',
|
neType: 'UPF',
|
||||||
neId: '001',
|
neId: upfWhoId.value,
|
||||||
startTime: nowDate - 5 * 60 * 1000,
|
startTime: nowDate - 5 * 60 * 1000,
|
||||||
endTime: nowDate,
|
endTime: nowDate,
|
||||||
|
|
||||||
interval: 5, // 5秒
|
interval: 5, // 5秒
|
||||||
sortField: 'timeGroup',
|
sortField: 'timeGroup',
|
||||||
sortOrder: 'asc',
|
sortOrder: 'asc',
|
||||||
|
|||||||
@@ -19,12 +19,15 @@ let dict: {
|
|||||||
ueEventType: DictType[];
|
ueEventType: DictType[];
|
||||||
/**UE 事件CM状态 */
|
/**UE 事件CM状态 */
|
||||||
ueEventCmState: DictType[];
|
ueEventCmState: DictType[];
|
||||||
|
/**CDR SIP响应代码类别类型 */
|
||||||
|
cdrSipCodeCause: DictType[];
|
||||||
} = reactive({
|
} = reactive({
|
||||||
cdrSipCode: [],
|
cdrSipCode: [],
|
||||||
cdrCallType: [],
|
cdrCallType: [],
|
||||||
ueAauthCode: [],
|
ueAauthCode: [],
|
||||||
ueEventType: [],
|
ueEventType: [],
|
||||||
ueEventCmState: [],
|
ueEventCmState: [],
|
||||||
|
cdrSipCodeCause: [],
|
||||||
});
|
});
|
||||||
|
|
||||||
onMounted(() => {
|
onMounted(() => {
|
||||||
@@ -35,6 +38,7 @@ onMounted(() => {
|
|||||||
getDict('ue_auth_code'),
|
getDict('ue_auth_code'),
|
||||||
getDict('ue_event_type'),
|
getDict('ue_event_type'),
|
||||||
getDict('ue_event_cm_state'),
|
getDict('ue_event_cm_state'),
|
||||||
|
getDict('cdr_sip_code_cause'),
|
||||||
]).then(resArr => {
|
]).then(resArr => {
|
||||||
if (resArr[0].status === 'fulfilled') {
|
if (resArr[0].status === 'fulfilled') {
|
||||||
dict.cdrSipCode = resArr[0].value;
|
dict.cdrSipCode = resArr[0].value;
|
||||||
@@ -51,6 +55,9 @@ onMounted(() => {
|
|||||||
if (resArr[4].status === 'fulfilled') {
|
if (resArr[4].status === 'fulfilled') {
|
||||||
dict.ueEventCmState = resArr[4].value;
|
dict.ueEventCmState = resArr[4].value;
|
||||||
}
|
}
|
||||||
|
if (resArr[5].status === 'fulfilled') {
|
||||||
|
dict.cdrSipCodeCause = resArr[5].value;
|
||||||
|
}
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
@@ -75,12 +82,7 @@ onMounted(() => {
|
|||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
<div></div>
|
<div></div>
|
||||||
<div>
|
<div></div>
|
||||||
{{ t('views.dashboard.overview.userActivity.time') }}:
|
|
||||||
<span :title="parseDateToStr(item.data.releaseTime * 1000)">
|
|
||||||
{{ parseDateToStr(item.data.releaseTime * 1000) }}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
<div class="card-cdr-item">
|
<div class="card-cdr-item">
|
||||||
<div>
|
<div>
|
||||||
@@ -101,6 +103,16 @@ onMounted(() => {
|
|||||||
</div>
|
</div>
|
||||||
<div v-else></div>
|
<div v-else></div>
|
||||||
</div>
|
</div>
|
||||||
|
<div>
|
||||||
|
{{ t('views.dashboard.overview.userActivity.time') }}:
|
||||||
|
<span :title="item.data.releaseTime">
|
||||||
|
{{
|
||||||
|
typeof item.data.releaseTime === 'number'
|
||||||
|
? parseDateToStr(+item.data.releaseTime * 1000)
|
||||||
|
: parseDateToStr(item.data.releaseTime)
|
||||||
|
}}
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
<div>
|
<div>
|
||||||
{{ t('views.dashboard.overview.userActivity.result') }}:
|
{{ t('views.dashboard.overview.userActivity.result') }}:
|
||||||
<span v-if="item.data.callType !== 'sms'">
|
<span v-if="item.data.callType !== 'sms'">
|
||||||
@@ -108,6 +120,11 @@ onMounted(() => {
|
|||||||
:options="dict.cdrSipCode"
|
:options="dict.cdrSipCode"
|
||||||
:value="item.data.cause"
|
:value="item.data.cause"
|
||||||
value-default="0"
|
value-default="0"
|
||||||
|
/>
|
||||||
|
<DictTag
|
||||||
|
:options="dict.cdrSipCodeCause"
|
||||||
|
:value="item.data.cause"
|
||||||
|
value-default="0"
|
||||||
/>
|
/>
|
||||||
</span>
|
</span>
|
||||||
<span v-else>
|
<span v-else>
|
||||||
@@ -131,21 +148,7 @@ onMounted(() => {
|
|||||||
<div>
|
<div>
|
||||||
IMSI: <span :title="item.data.imsi">{{ item.data.imsi }}</span>
|
IMSI: <span :title="item.data.imsi">{{ item.data.imsi }}</span>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div></div>
|
||||||
{{ t('views.dashboard.overview.userActivity.time') }}:
|
|
||||||
<span
|
|
||||||
v-if="item.type === 'auth-result'"
|
|
||||||
:title="item.data.authTime"
|
|
||||||
>
|
|
||||||
{{ item.data.authTime }}
|
|
||||||
</span>
|
|
||||||
<span v-if="item.type === 'detach'" :title="item.data.detachTime">
|
|
||||||
{{ item.data.detachTime }}
|
|
||||||
</span>
|
|
||||||
<span v-if="item.type === 'cm-state'" :title="item.data.changeTime">
|
|
||||||
{{ item.data.changeTime }}
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="card-ue-w33" v-if="item.type === 'auth-result'">
|
<div class="card-ue-w33" v-if="item.type === 'auth-result'">
|
||||||
@@ -159,11 +162,20 @@ onMounted(() => {
|
|||||||
TAC ID: <span>{{ item.data.tacID }}</span>
|
TAC ID: <span>{{ item.data.tacID }}</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div>
|
||||||
|
{{ t('views.dashboard.overview.userActivity.time') }}:
|
||||||
|
<template v-if="item.data?.time">
|
||||||
|
{{ parseDateToStr(item.data.time) }}
|
||||||
|
</template>
|
||||||
|
<template v-else-if="item.data?.timestamp">
|
||||||
|
{{ parseDateToStr(+item.data.timestamp * 1000) }}
|
||||||
|
</template>
|
||||||
|
<template v-else> - </template>
|
||||||
|
</div>
|
||||||
<div v-if="item.type === 'auth-result'">
|
<div v-if="item.type === 'auth-result'">
|
||||||
{{ t('views.dashboard.overview.userActivity.result') }}:
|
{{ t('views.dashboard.overview.userActivity.result') }}:
|
||||||
<span>
|
<span>
|
||||||
<DictTag :options="dict.ueAauthCode" :value="item.data.authCode" />
|
<DictTag :options="dict.ueAauthCode" :value="item.data.result" />
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
<div v-if="item.type === 'detach'">
|
<div v-if="item.type === 'detach'">
|
||||||
@@ -173,7 +185,7 @@ onMounted(() => {
|
|||||||
<div class="card-ue-w33" v-if="item.type === 'cm-state'">
|
<div class="card-ue-w33" v-if="item.type === 'cm-state'">
|
||||||
{{ t('views.dashboard.overview.userActivity.result') }}:
|
{{ t('views.dashboard.overview.userActivity.result') }}:
|
||||||
<span>
|
<span>
|
||||||
<DictTag :options="dict.ueEventCmState" :value="item.data.status" />
|
<DictTag :options="dict.ueEventCmState" :value="item.data.result" />
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
@@ -189,7 +201,7 @@ onMounted(() => {
|
|||||||
<span v-if="item.type === 'cm-state'">
|
<span v-if="item.type === 'cm-state'">
|
||||||
{{
|
{{
|
||||||
dict.ueEventType
|
dict.ueEventType
|
||||||
.find(s => s.value === item.type)
|
.find((s: any) => s.value === item.type)
|
||||||
?.label.replace('CM', 'ECM')
|
?.label.replace('CM', 'ECM')
|
||||||
}}
|
}}
|
||||||
</span>
|
</span>
|
||||||
@@ -198,14 +210,9 @@ onMounted(() => {
|
|||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
<div>
|
<div>
|
||||||
IMSI: <span :title="item.data.imsi">{{ item.data.imsi }}</span>
|
IMSI: <span :title="item.data?.imsi">{{ item.data?.imsi }}</span>
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
{{ t('views.dashboard.overview.userActivity.time') }}:
|
|
||||||
<span :title="item.data.timestamp">
|
|
||||||
{{ parseDateToStr(+item.data.timestamp * 1000) }}
|
|
||||||
</span>
|
|
||||||
</div>
|
</div>
|
||||||
|
<div></div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="card-ue-w33" v-if="item.type === 'auth-result'">
|
<div class="card-ue-w33" v-if="item.type === 'auth-result'">
|
||||||
@@ -219,6 +226,20 @@ onMounted(() => {
|
|||||||
TAC ID: <span>{{ item.data.tacID }}</span>
|
TAC ID: <span>{{ item.data.tacID }}</span>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div>
|
||||||
|
{{ t('views.dashboard.overview.userActivity.time') }}:
|
||||||
|
<template v-if="item.data?.time">
|
||||||
|
{{ parseDateToStr(item.data.time) }}
|
||||||
|
</template>
|
||||||
|
<template v-else-if="item.data?.timestamp">
|
||||||
|
{{
|
||||||
|
typeof item.data?.timestamp === 'number'
|
||||||
|
? parseDateToStr(+item.data?.timestamp * 1000)
|
||||||
|
: parseDateToStr(item.data?.timestamp)
|
||||||
|
}}
|
||||||
|
</template>
|
||||||
|
<template v-else> - </template>
|
||||||
|
</div>
|
||||||
<div v-if="item.type === 'auth-result'">
|
<div v-if="item.type === 'auth-result'">
|
||||||
{{ t('views.dashboard.overview.userActivity.result') }}:
|
{{ t('views.dashboard.overview.userActivity.result') }}:
|
||||||
<span>
|
<span>
|
||||||
|
|||||||
@@ -16,6 +16,8 @@
|
|||||||
.column {
|
.column {
|
||||||
flex: 3;
|
flex: 3;
|
||||||
position: relative;
|
position: relative;
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 边框 */
|
/* 边框 */
|
||||||
@@ -79,13 +81,14 @@
|
|||||||
.upfFlow .inner .chart {
|
.upfFlow .inner .chart {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
height: 100%;
|
height: 100%;
|
||||||
margin-top: 1rem;
|
margin-top: 0rem;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* 网络拓扑 */
|
/* 网络拓扑 */
|
||||||
.topology {
|
.topology {
|
||||||
/* min-height: 27.8rem; */
|
/* min-height: 27.8rem; */
|
||||||
height: 56.4%;
|
height: 56.4%;
|
||||||
|
flex: 1;
|
||||||
}
|
}
|
||||||
.topology .inner h3 {
|
.topology .inner h3 {
|
||||||
display: flex;
|
display: flex;
|
||||||
@@ -125,6 +128,19 @@
|
|||||||
align-items: baseline;
|
align-items: baseline;
|
||||||
width: 33%;
|
width: 33%;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Subscriber Information部分的宽度调整 */
|
||||||
|
.skim .inner .data .item:nth-child(1) {
|
||||||
|
width: 38%; /* Total Subscriber Base - 稍微宽一点 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.skim .inner .data .item:nth-child(2) {
|
||||||
|
width: 33%; /* VoLTE - 保持不变 */
|
||||||
|
}
|
||||||
|
|
||||||
|
.skim .inner .data .item:nth-child(3) {
|
||||||
|
width: 29%; /* VoIP - 稍微窄一点 */
|
||||||
|
}
|
||||||
.skim .inner .data .item div {
|
.skim .inner .data .item div {
|
||||||
font-size: 1.467rem;
|
font-size: 1.467rem;
|
||||||
color: #fff;
|
color: #fff;
|
||||||
@@ -179,6 +195,7 @@
|
|||||||
.userActivity {
|
.userActivity {
|
||||||
/* min-height: 35.8rem; */
|
/* min-height: 35.8rem; */
|
||||||
height: 54.6%;
|
height: 54.6%;
|
||||||
|
flex: 1;
|
||||||
}
|
}
|
||||||
.userActivity .inner .chart {
|
.userActivity .inner .chart {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
@@ -259,6 +276,7 @@
|
|||||||
.alarmType {
|
.alarmType {
|
||||||
/* min-height: 25rem; */
|
/* min-height: 25rem; */
|
||||||
height: 46%;
|
height: 46%;
|
||||||
|
flex: 1;
|
||||||
}
|
}
|
||||||
.alarmType .inner .chart {
|
.alarmType .inner .chart {
|
||||||
width: 100%;
|
width: 100%;
|
||||||
|
|||||||