push потерянного файла
This commit is contained in:
parent
952ba3b588
commit
5e3666e899
|
|
@ -0,0 +1,122 @@
|
|||
import $ from 'jquery';
|
||||
import { JSONRPC } from '@/json-rpc.js';
|
||||
|
||||
let resourcesData = {
|
||||
domains: [],
|
||||
subnets: [],
|
||||
ASN: []
|
||||
};
|
||||
|
||||
function escapeHtml(value) {
|
||||
return String(value)
|
||||
.replace(/&/g, '&')
|
||||
.replace(/</g, '<')
|
||||
.replace(/>/g, '>')
|
||||
.replace(/"/g, '"')
|
||||
.replace(/'/g, ''');
|
||||
}
|
||||
|
||||
function buildAsnLink(asn) {
|
||||
const numericPart = String(asn).match(/\d+/);
|
||||
const asnId = numericPart ? numericPart[0] : String(asn).replace(/[^a-zA-Z0-9]/g, '');
|
||||
const safeId = asnId.length ? asnId : '0';
|
||||
return `https://bgp.he.net/AS${encodeURIComponent(safeId)}`;
|
||||
}
|
||||
|
||||
function normalizeArray(values) {
|
||||
if (!Array.isArray(values)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
return values
|
||||
.map(item => (item === null || item === undefined) ? '' : String(item))
|
||||
.filter(item => item.length > 0)
|
||||
.sort((a, b) => a.localeCompare(b, 'ru', { numeric: true, sensitivity: 'base' }));
|
||||
}
|
||||
|
||||
async function fetchResources() {
|
||||
try {
|
||||
const result = await JSONRPC.NetworkManager.getOutputResources();
|
||||
resourcesData = {
|
||||
domains: normalizeArray(result?.domains),
|
||||
subnets: normalizeArray(result?.subnets),
|
||||
ASN: normalizeArray(result?.ASN)
|
||||
};
|
||||
return true;
|
||||
} catch (error) {
|
||||
console.error('Ошибка при загрузке сетевых ресурсов:', error);
|
||||
resourcesData = {
|
||||
domains: [],
|
||||
subnets: [],
|
||||
ASN: []
|
||||
};
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
function renderAsnSection(items) {
|
||||
const content = items.length
|
||||
? items.map(item => `<a class="network-resource-link" href="${buildAsnLink(item)}" target="_blank" rel="noopener noreferrer">${escapeHtml(item)}</a>`).join(', ')
|
||||
: 'Данные отсутствуют';
|
||||
|
||||
return `
|
||||
<section class="card" style="margin-bottom: 24px;">
|
||||
<h2 class="card-title">Автономные системы (ASN)</h2>
|
||||
<p>${content}</p>
|
||||
</section>
|
||||
`;
|
||||
}
|
||||
|
||||
function renderGridSection(title, items) {
|
||||
const listItems = items.length
|
||||
? items.map(item => `<li class="subscription-item" style="margin: 0;">${escapeHtml(item)}</li>`).join('')
|
||||
: '<li class="subscription-item" style="grid-column: 1 / -1; margin: 0;">Данные отсутствуют</li>';
|
||||
|
||||
return `
|
||||
<section class="card" style="margin-bottom: 24px;">
|
||||
<h2 class="card-title">${title}</h2>
|
||||
<ul class="subscription-list" style="display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 12px;">
|
||||
${listItems}
|
||||
</ul>
|
||||
</section>
|
||||
`;
|
||||
}
|
||||
|
||||
function renderResources($container) {
|
||||
const html = `
|
||||
${renderAsnSection(resourcesData.ASN)}
|
||||
${renderGridSection('Доменные имена', resourcesData.domains)}
|
||||
${renderGridSection('Маршруты', resourcesData.subnets)}
|
||||
`;
|
||||
|
||||
$container.html(html);
|
||||
}
|
||||
|
||||
export const NetworkResourcesPage = {
|
||||
render: () => `
|
||||
<div>
|
||||
<h1 class="page-title">Сетевые ресурсы</h1>
|
||||
<div id="network-resources-content">
|
||||
<p>Загрузка сетевых ресурсов...</p>
|
||||
</div>
|
||||
</div>
|
||||
`,
|
||||
mount: async () => {
|
||||
const $container = $('#network-resources-content');
|
||||
$container.html('<p>Загрузка сетевых ресурсов...</p>');
|
||||
|
||||
const success = await fetchResources();
|
||||
if (success) {
|
||||
renderResources($container);
|
||||
} else {
|
||||
$container.html('<p class="error-message">Не удалось загрузить данные. Попробуйте обновить страницу позже.</p>');
|
||||
}
|
||||
},
|
||||
unmount: () => {
|
||||
resourcesData = {
|
||||
domains: [],
|
||||
subnets: [],
|
||||
ASN: []
|
||||
};
|
||||
}
|
||||
};
|
||||
Loading…
Reference in New Issue