Убраны LXC-шаблоны по VMID из интерфейса

This commit is contained in:
2026-08-09 18:41:03 +03:00
parent d02a86f8f1
commit 94185ac1e6
+38 -41
View File
@@ -37,8 +37,9 @@ export default function AdminTemplates() {
}
async function importVm(vm) {
const key = `vm-${vm.vmid}`;
setError("");
setImporting(`vm-${vm.vmid}`);
setImporting(key);
try {
await api.createTemplate({
name: vm.name || `VM-${vm.vmid}`,
@@ -57,19 +58,19 @@ export default function AdminTemplates() {
}
}
async function importLxc(lxc) {
async function importLxc(archive) {
const key = `lxc-${archive.volid}`;
setError("");
const key = lxc.vmid ? `lxc-vmid-${lxc.vmid}` : `lxc-${lxc.volid}`;
setImporting(key);
try {
await api.createTemplate({
name: lxc.name || (lxc.vmid ? `LXC-${lxc.vmid}` : "LXC"),
name: archive.name,
guest_type: "lxc",
source_vmid: lxc.vmid ? Number(lxc.vmid) : null,
source_template: lxc.vmid ? null : lxc.volid,
cores: lxc.cores || 1,
memory_mb: lxc.memory_mb || 1024,
disk_gb: lxc.disk_gb || 8,
source_vmid: null,
source_template: archive.volid,
cores: 1,
memory_mb: 1024,
disk_gb: 8,
});
await refresh();
} catch (err) {
@@ -140,44 +141,37 @@ export default function AdminTemplates() {
{vmTemplates.length > 0 ? (
<table className="data-table">
<thead><tr><th>VMID</th><th>Имя</th><th>vCPU</th><th>RAM</th><th /></tr></thead>
<tbody>
{vmTemplates.map((vm) => {
const key = `vm-${vm.vmid}`;
return (
<tr key={key}>
<td>{vm.vmid}</td><td>{vm.name}</td><td>{vm.cores}</td><td>{vm.memory_mb} МБ</td>
<td><button className="btn btn-primary" disabled={importing === key} onClick={() => importVm(vm)}>{importing === key ? "Импорт…" : "Импорт"}</button></td>
</tr>
);
})}
</tbody>
<tbody>{vmTemplates.map((vm) => {
const key = `vm-${vm.vmid}`;
return (
<tr key={key}>
<td>{vm.vmid}</td><td>{vm.name}</td><td>{vm.cores}</td><td>{vm.memory_mb} МБ</td>
<td><button className="btn btn-primary" disabled={importing === key} onClick={() => importVm(vm)}>{importing === key ? "Импорт…" : "Импорт"}</button></td>
</tr>
);
})}</tbody>
</table>
) : <p className="muted">VM-шаблоны не найдены.</p>}
</section>
<section>
<h4>📦 LXC-шаблоны</h4>
<h4>📦 Архивные LXC-шаблоны</h4>
{lxcTemplates.length > 0 ? (
<table className="data-table">
<thead><tr><th>VMID</th><th>Имя</th><th>Источник</th><th>vCPU</th><th>RAM</th><th /></tr></thead>
<tbody>
{lxcTemplates.map((lxc, index) => {
const key = lxc.vmid ? `lxc-vmid-${lxc.vmid}` : `lxc-${lxc.volid || index}`;
const source = lxc.vmid ? "LXC-контейнер" : `${lxc.storage || "—"}: vzdump`;
return (
<tr key={key}>
<td>{lxc.vmid || "—"}</td>
<td>{lxc.name}</td>
<td>{source}</td>
<td>{lxc.cores || 1}</td>
<td>{lxc.memory_mb || `${lxc.size_mb || 0} МБ`}</td>
<td><button className="btn btn-primary" disabled={importing === key} onClick={() => importLxc(lxc)}>{importing === key ? "Импорт…" : "Импорт"}</button></td>
</tr>
);
})}
</tbody>
<thead><tr><th>Имя</th><th>Хранилище</th><th>Размер</th><th /></tr></thead>
<tbody>{lxcTemplates.map((archive) => {
const key = `lxc-${archive.volid}`;
return (
<tr key={key}>
<td>{archive.name}</td>
<td>{archive.storage || "—"}</td>
<td>{archive.size_mb || 0} МБ</td>
<td><button className="btn btn-primary" disabled={importing === key} onClick={() => importLxc(archive)}>{importing === key ? "Импорт…" : "Импорт"}</button></td>
</tr>
);
})}</tbody>
</table>
) : <p className="muted">LXC-шаблоны не найдены.</p>}
) : <p className="muted">Архивные LXC-шаблоны не найдены.</p>}
</section>
</div>
)}
@@ -188,8 +182,11 @@ export default function AdminTemplates() {
<div className="template-form-grid">
<div className="field"><label>Название</label><input value={form.name} onChange={(e) => set("name", e.target.value)} required /></div>
<div className="field"><label>Тип</label><select value={form.guest_type} onChange={(e) => set("guest_type", e.target.value)}><option value="vm">VM</option><option value="lxc">LXC</option></select></div>
{form.guest_type === "vm" ? <div className="field"><label>VMID шаблона</label><input type="number" value={form.source_vmid} onChange={(e) => set("source_vmid", e.target.value)} placeholder="999" required /></div>
: <div className="field"><label>CT-шаблон (volid)</label><input value={form.source_template} onChange={(e) => set("source_template", e.target.value)} placeholder="local:vztmpl/..." required /> </div>}
{form.guest_type === "vm" ? (
<div className="field"><label>VMID шаблона</label><input type="number" value={form.source_vmid} onChange={(e) => set("source_vmid", e.target.value)} placeholder="999" required /></div>
) : (
<div className="field"><label>Архив LXC-шаблона</label><input value={form.source_template} onChange={(e) => set("source_template", e.target.value)} placeholder="local:vztmpl/..." required /></div>
)}
<div className="field"><label>Описание</label><input value={form.description} onChange={(e) => set("description", e.target.value)} /></div>
<div className="field"><label>vCPU</label><input type="number" min={1} value={form.cores} onChange={(e) => set("cores", e.target.value)} /></div>
<div className="field"><label>RAM, МБ</label><input type="number" min={256} step={256} value={form.memory_mb} onChange={(e) => set("memory_mb", e.target.value)} /></div>