diff --git a/locale/tr/LC_MESSAGES/django.mo b/locale/tr/LC_MESSAGES/django.mo index e761dca8..fe346aaf 100644 Binary files a/locale/tr/LC_MESSAGES/django.mo and b/locale/tr/LC_MESSAGES/django.mo differ diff --git a/locale/tr/LC_MESSAGES/django.po b/locale/tr/LC_MESSAGES/django.po index aed2db29..27d1938f 100644 --- a/locale/tr/LC_MESSAGES/django.po +++ b/locale/tr/LC_MESSAGES/django.po @@ -11,7 +11,7 @@ msgid "" msgstr "" "Project-Id-Version: PACKAGE VERSION\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2026-11-07 19:47+0000\n" +"POT-Creation-Date: 2026-11-07 20:40+0000\n" "PO-Revision-Date: 2020-11-04 12:00+0000\n" "Last-Translator: catborise , 2020\n" "Language-Team: Turkish (https://www.transifex.com/catborise/teams/110663/tr/)\n" @@ -2792,7 +2792,7 @@ msgstr "" msgid "Delete snapshot" msgstr "Anlık görüntüyü sil" -#: instances/jobs.py:317 vrtManager/instance.py:2297 +#: instances/jobs.py:317 vrtManager/instance.py:2300 #, python-format msgid "The VM has no external snapshot named %(name)s" msgstr "Sanal makinede %(name)s adında harici anlık görüntü yok" @@ -2827,7 +2827,7 @@ msgstr "Sanal makine artık işin çalıştığı sunucuda değil" msgid "Take snapshot" msgstr "Anlık görüntü al" -#: instances/jobs.py:385 instances/jobs.py:394 vrtManager/instance.py:1893 +#: instances/jobs.py:385 instances/jobs.py:394 vrtManager/instance.py:1896 #, python-format msgid "A snapshot named %(name)s already exists" msgstr "%(name)s adında bir anlık görüntü zaten var" @@ -3025,7 +3025,7 @@ msgstr "cloud-init tohumu, disk için bir dizin depolama havuzu gerektirir" msgid "This host offers no firmware %(firmware)s" msgstr "Bu sunucu %(firmware)s firmware'ini sunmuyor" -#: instances/jobs.py:838 vrtManager/instance.py:3029 +#: instances/jobs.py:838 vrtManager/instance.py:3032 msgid "This host offers no TPM 2.0: install swtpm on it" msgstr "Bu sunucu TPM 2.0 sunmuyor: üzerine swtpm kurun" @@ -5919,16 +5919,16 @@ msgstr "%(quota)s (%(total)s > %(limit)s)" msgid "None available device name" msgstr "Hiçbiri uygun aygıt adı değil" -#: instances/utils.py:434 +#: instances/utils.py:435 #, python-format msgid "%(hostname)s via %(address)s" msgstr "%(address)s üzerinden %(hostname)s" -#: instances/utils.py:473 +#: instances/utils.py:474 msgid "Invalid MAC address" msgstr "Geçersiz MAC adresi" -#: instances/utils.py:475 +#: instances/utils.py:476 msgid "More MAC addresses than networks" msgstr "Ağlardan daha fazla MAC adresi" @@ -8048,51 +8048,51 @@ msgstr "İmaj adı 120 karakterden fazla olamaz" msgid "Clone volume" msgstr "Birimi klonla" -#: storages/jobs.py:59 storages/jobs.py:70 +#: storages/jobs.py:60 storages/jobs.py:73 msgid "Name of volume already in use" msgstr "Birim adı zaten kullanılıyor" -#: storages/jobs.py:65 +#: storages/jobs.py:67 #, python-format msgid "The pool has no volume named %(name)s" msgstr "Havuzda %(name)s adında birim yok" -#: storages/jobs.py:67 +#: storages/jobs.py:69 msgid "An ISO image is not cloned" msgstr "ISO imajı klonlanmaz" -#: storages/jobs.py:79 +#: storages/jobs.py:82 msgid "Copying the volume" msgstr "Birim kopyalanıyor" -#: storages/jobs.py:91 +#: storages/jobs.py:94 msgid "" "The copy exists, but the job did not see it finish; check it, then resolve " "this job." msgstr "" "Kopya var, ancak iş bittiğini görmedi; kontrol edin, sonra bu işi çözün." -#: storages/jobs.py:92 +#: storages/jobs.py:95 msgid "The copy was not made" msgstr "Kopya oluşturulmadı" -#: storages/jobs.py:103 +#: storages/jobs.py:106 msgid "Upload ISO image" msgstr "ISO imajı yükle" -#: storages/jobs.py:118 +#: storages/jobs.py:121 msgid "Invalid file name" msgstr "Geçersiz dosya adı" -#: storages/jobs.py:120 +#: storages/jobs.py:123 msgid "Only .iso files can be uploaded" msgstr "Yalnızca .iso dosyaları yüklenebilir" -#: storages/jobs.py:122 +#: storages/jobs.py:125 msgid "Invalid file size" msgstr "Geçersiz dosya boyutu" -#: storages/jobs.py:124 +#: storages/jobs.py:127 msgid "Invalid chunk index or total chunks" msgstr "Geçersiz parça dizini veya toplam parça sayısı" @@ -9012,17 +9012,17 @@ msgstr "" "%(target)s (%(path)s): hedef sunucunun %(pool)s havuzunda zaten %(file)s " "dosyası var" -#: vrtManager/instance.py:375 +#: vrtManager/instance.py:378 #, python-format msgid "%(target)s (%(path)s): another disk is copied to %(dest)s" msgstr "%(target)s (%(path)s): başka bir disk %(dest)s konumuna kopyalanıyor" -#: vrtManager/instance.py:380 +#: vrtManager/instance.py:383 #, python-format msgid "%(target)s: the VM has no disk file to copy" msgstr "%(target)s: sanal makinenin kopyalanacak disk dosyası yok" -#: vrtManager/instance.py:384 +#: vrtManager/instance.py:387 #, python-format msgid "" "%(target)s (%(path)s) of the next start: the destination host does not share " @@ -9031,12 +9031,12 @@ msgstr "" "Sonraki başlatmanın %(target)s (%(path)s) diski: hedef sunucu bunu " "paylaşmıyor" -#: vrtManager/instance.py:388 +#: vrtManager/instance.py:391 #, python-format msgid "The disks cannot be migrated: %(problems)s" msgstr "Diskler taşınamaz: %(problems)s" -#: vrtManager/instance.py:401 +#: vrtManager/instance.py:404 #, python-format msgid "" "%(error)s; remove the partial disk copies from the destination host: " @@ -9044,14 +9044,14 @@ msgid "" msgstr "" "%(error)s; yarım kalan disk kopyalarını hedef sunucudan kaldırın: %(copies)s" -#: vrtManager/instance.py:418 +#: vrtManager/instance.py:421 #, python-format msgid "" "%(error)s; remove the partial disk copies from the destination host: %(left)s" msgstr "" "%(error)s; yarım kalan disk kopyalarını hedef sunucudan kaldırın: %(left)s" -#: vrtManager/instance.py:432 +#: vrtManager/instance.py:435 #, python-format msgid "" "The NVRAM file %(path)s is not in libvirt's NVRAM directory %(dir)s and " @@ -9060,26 +9060,26 @@ msgstr "" "%(path)s NVRAM dosyası libvirt'in NVRAM dizini %(dir)s içinde değil ve " "kopyalanamaz" -#: vrtManager/instance.py:441 +#: vrtManager/instance.py:444 #, python-format msgid "The destination host cannot see the NVRAM file %(path)s" msgstr "Hedef sunucu %(path)s NVRAM dosyasını göremiyor" -#: vrtManager/instance.py:517 +#: vrtManager/instance.py:520 #, python-format msgid "%(type)s disk, cannot be checked" msgstr "%(type)s disk, kontrol edilemiyor" -#: vrtManager/instance.py:557 +#: vrtManager/instance.py:560 #, python-format msgid "The destination host already has a VM %(key)s" msgstr "Hedef sunucuda zaten %(key)s sanal makinesi var" -#: vrtManager/instance.py:579 +#: vrtManager/instance.py:582 msgid "The VM was started on the source host during the migration" msgstr "Sanal makine taşıma sırasında kaynak sunucuda başlatıldı" -#: vrtManager/instance.py:595 +#: vrtManager/instance.py:598 #, python-format msgid "" "%(error)s; the VM may now be defined only on the destination host: check both" @@ -9088,7 +9088,7 @@ msgstr "" "%(error)s; sanal makine artık yalnızca hedef sunucuda tanımlı olabilir: iki " "sunucuyu da kontrol edin" -#: vrtManager/instance.py:601 +#: vrtManager/instance.py:604 #, python-format msgid "" "%(error)s; the VM is now defined on both hosts, remove it from the " @@ -9097,7 +9097,7 @@ msgstr "" "%(error)s; sanal makine artık iki sunucuda da tanımlı, hedeften kaldırın: " "%(undo_error)s" -#: vrtManager/instance.py:607 +#: vrtManager/instance.py:610 msgid "" "Snapshot names are 1-64 letters, digits, '.', '_' or '-' and do not start " "with '.'" @@ -9105,7 +9105,7 @@ msgstr "" "Anlık görüntü adları 1-64 harf, rakam, '.', '_' veya '-' karakterinden oluşur" " ve '.' ile başlamaz" -#: vrtManager/instance.py:1095 +#: vrtManager/instance.py:1098 msgid "" "A device other than a disk or NIC is in the boot order: change it in the XML " "editor" @@ -9113,104 +9113,104 @@ msgstr "" "Önyükleme sırasında disk veya NIC dışında bir aygıt var: bunu XML " "düzenleyicide değiştirin" -#: vrtManager/instance.py:1107 +#: vrtManager/instance.py:1110 msgid "Invalid Device Type for boot order" msgstr "Ön yükleme sırası için geçersiz aygıt türü" -#: vrtManager/instance.py:1110 +#: vrtManager/instance.py:1113 #, python-format msgid "Boot device %(dev)s is not in the definition" msgstr "Ön yükleme aygıtı %(dev)s tanımda yok" -#: vrtManager/instance.py:1130 +#: vrtManager/instance.py:1133 #, python-format msgid "CD-ROM %(dev)s is not in the running definition" msgstr "CD-ROM %(dev)s çalışan tanımda yok" -#: vrtManager/instance.py:1131 +#: vrtManager/instance.py:1134 #, python-format msgid "CD-ROM %(dev)s is not in the persistent definition" msgstr "CD-ROM %(dev)s kalıcı tanımda yok" -#: vrtManager/instance.py:1143 +#: vrtManager/instance.py:1146 #, python-format msgid "Media of %(dev)s changed in the running VM only: %(err)s" msgstr "%(dev)s ortamı yalnızca çalışan sanal makinede değişti: %(err)s" -#: vrtManager/instance.py:1154 +#: vrtManager/instance.py:1157 #, python-format msgid "ISO image %(image)s was not found" msgstr "ISO imajı %(image)s bulunamadı" -#: vrtManager/instance.py:1156 +#: vrtManager/instance.py:1159 #, python-format msgid "ISO image %(image)s is in more than one storage pool" msgstr "ISO imajı %(image)s birden fazla depolama havuzunda var" -#: vrtManager/instance.py:1263 +#: vrtManager/instance.py:1266 #, python-format msgid "Disk %(target_dev)s is not in the VM's definition" msgstr "Disk %(target_dev)s sanal makinenin tanımında yok" -#: vrtManager/instance.py:1391 +#: vrtManager/instance.py:1394 msgid "Please shutdown the instance then try to enable vCPU hotplug" msgstr "" "vCPU hotplug özelliğini etkinleştirmek için önce sanal makineyi kapatın" -#: vrtManager/instance.py:1678 +#: vrtManager/instance.py:1681 msgid "The VM has no video card" msgstr "Sanal makinede ekran kartı yok" -#: vrtManager/instance.py:1852 +#: vrtManager/instance.py:1855 msgid "" "The VM has external snapshots; internal snapshots cannot be mixed with them" msgstr "" "Sanal makinenin harici anlık görüntüleri var; dahili anlık görüntüler " "bunlarla karıştırılamaz" -#: vrtManager/instance.py:1884 +#: vrtManager/instance.py:1887 msgid "A snapshot with memory is not quiesced; it keeps the whole guest state" msgstr "" "Bellekli bir anlık görüntüde dosya sistemleri dondurulmaz; tüm konuk durumunu" " saklar" -#: vrtManager/instance.py:1886 +#: vrtManager/instance.py:1889 msgid "Only a running VM's file systems can be frozen" msgstr "Yalnızca çalışan bir sanal makinenin dosya sistemleri dondurulabilir" -#: vrtManager/instance.py:1888 +#: vrtManager/instance.py:1891 msgid "The QEMU guest agent is not connected; it freezes the file systems" msgstr "QEMU konuk aracısı bağlı değil; dosya sistemlerini o dondurur" -#: vrtManager/instance.py:1891 +#: vrtManager/instance.py:1894 msgid "" "The VM has internal snapshots; external snapshots cannot be mixed with them" msgstr "" "Sanal makinenin dahili anlık görüntüleri var; harici anlık görüntüler " "bunlarla karıştırılamaz" -#: vrtManager/instance.py:1896 +#: vrtManager/instance.py:1899 msgid "Newer snapshots exist after the last revert; delete them first" msgstr "" "Son geri dönüşten sonra daha yeni anlık görüntüler var; önce onları silin" -#: vrtManager/instance.py:1899 +#: vrtManager/instance.py:1902 msgid "No snapshot is current; revert to a snapshot first" msgstr "Geçerli anlık görüntü yok; önce bir anlık görüntüye geri dönün" -#: vrtManager/instance.py:1905 +#: vrtManager/instance.py:1908 #, python-format msgid "Eject the media from %(dev)s first" msgstr "Önce %(dev)s içindeki ortamı çıkarın" -#: vrtManager/instance.py:1907 +#: vrtManager/instance.py:1910 #, python-format msgid "Disk %(dev)s is not a file; external snapshots need file disks" msgstr "" "Disk %(dev)s bir dosya değil; harici anlık görüntüler dosya diskleri " "gerektirir" -#: vrtManager/instance.py:1915 +#: vrtManager/instance.py:1918 #, python-format msgid "" "The storage pools could not be refreshed, so their free space is unknown: " @@ -9218,21 +9218,21 @@ msgid "" msgstr "" "Depolama havuzları yenilenemedi, bu yüzden boş alanları bilinmiyor: %(err)s" -#: vrtManager/instance.py:1936 +#: vrtManager/instance.py:1939 msgid "Memory is saved only from a running VM" msgstr "Bellek yalnızca çalışan bir sanal makineden kaydedilir" -#: vrtManager/instance.py:1938 +#: vrtManager/instance.py:1941 msgid "The VM has no disk to keep its memory next to" msgstr "Sanal makinenin, belleğinin yanına kaydedileceği bir diski yok" -#: vrtManager/instance.py:1942 +#: vrtManager/instance.py:1945 #, python-format msgid "%(disk)s is not in a storage pool; memory is saved only into one" msgstr "" "%(disk)s bir depolama havuzunda değil; bellek yalnızca bir havuza kaydedilir" -#: vrtManager/instance.py:1973 +#: vrtManager/instance.py:1976 #, python-format msgid "" "Storage pool %(pool)s has %(free).1f GiB free; the snapshot needs %(size).1f " @@ -9243,7 +9243,7 @@ msgstr "" "%(size).1f GiB gerektiriyor (sanal makinenin oradaki disklerinin " "%%%(percent)g kadarı, en az %(minimum)g GiB, ve kaydediliyorsa bellek)" -#: vrtManager/instance.py:1991 +#: vrtManager/instance.py:1994 msgid "" "This snapshot was taken by an older version on a UEFI VM and cannot be " "reverted; delete it instead" @@ -9251,7 +9251,7 @@ msgstr "" "Bu anlık görüntü UEFI bir sanal makinede eski bir sürümle alındı ve geri " "dönülemez; bunun yerine silin" -#: vrtManager/instance.py:2021 +#: vrtManager/instance.py:2024 #, python-format msgid "" "The revert failed twice; try again in a moment (%(error)s). The VM is " @@ -9260,7 +9260,7 @@ msgstr "" "Geri dönüş iki kez başarısız oldu; biraz sonra tekrar deneyin (%(error)s). " "Sanal makine çalışıyor." -#: vrtManager/instance.py:2023 +#: vrtManager/instance.py:2026 #, python-format msgid "" "The revert failed twice; try again in a moment (%(error)s). The VM is shut " @@ -9269,13 +9269,13 @@ msgstr "" "Geri dönüş iki kez başarısız oldu; biraz sonra tekrar deneyin (%(error)s). " "Sanal makine kapalı." -#: vrtManager/instance.py:2186 +#: vrtManager/instance.py:2189 msgid "A disk moves when its VM is defined and running, paused or shut off" msgstr "" "Bir disk, sanal makinesi tanımlıyken ve çalışırken, duraklatılmışken veya " "kapalıyken taşınır" -#: vrtManager/instance.py:2188 +#: vrtManager/instance.py:2191 msgid "" "A disk of a VM with snapshots, a saved state or a running block job does not " "move" @@ -9283,7 +9283,7 @@ msgstr "" "Anlık görüntüleri, kaydedilmiş durumu veya çalışan bir blok işi olan sanal " "makinenin diski taşınmaz" -#: vrtManager/instance.py:2196 +#: vrtManager/instance.py:2199 #, python-format msgid "" "%(dev)s is not a disk file of the VM, the same in its running and next " @@ -9292,132 +9292,132 @@ msgstr "" "%(dev)s, sanal makinenin çalışan ve sonraki başlatma tanımlarında aynı olan " "bir disk dosyası değil" -#: vrtManager/instance.py:2201 +#: vrtManager/instance.py:2204 #, python-format msgid "%(dev)s does not move: only writable raw and qcow2 disks do" msgstr "%(dev)s taşınmaz: yalnızca yazılabilir raw ve qcow2 diskler taşınır" -#: vrtManager/instance.py:2208 +#: vrtManager/instance.py:2211 #, python-format msgid "%(dev)s does not move: no storage pool has %(path)s" msgstr "%(dev)s taşınmaz: hiçbir depolama havuzunda %(path)s yok" -#: vrtManager/instance.py:2210 +#: vrtManager/instance.py:2213 #, python-format msgid "%(dev)s does not move: it has a backing file" msgstr "%(dev)s taşınmaz: temel (backing) dosyası var" -#: vrtManager/instance.py:2213 +#: vrtManager/instance.py:2216 #, python-format msgid "%(pool_name)s is not an active pool of disk files of this host" msgstr "%(pool_name)s bu sunucunun etkin bir disk dosyası havuzu değil" -#: vrtManager/instance.py:2216 +#: vrtManager/instance.py:2219 #, python-format msgid "%(dev)s is in pool %(pool_name)s already" msgstr "%(dev)s zaten %(pool_name)s havuzunda" -#: vrtManager/instance.py:2220 +#: vrtManager/instance.py:2223 #, python-format msgid "Pool %(pool_name)s already has a file %(name)s" msgstr "%(pool_name)s havuzunda zaten %(name)s dosyası var" -#: vrtManager/instance.py:2244 +#: vrtManager/instance.py:2247 #, python-format msgid "The copy of %(dev)s ended before it was complete" msgstr "%(dev)s kopyası tamamlanmadan sona erdi" -#: vrtManager/instance.py:2289 +#: vrtManager/instance.py:2292 #, python-format msgid "%(error)s; remove %(dest)s if it is there: %(cleanup_error)s" msgstr "%(error)s; varsa %(dest)s dosyasını kaldırın: %(cleanup_error)s" -#: vrtManager/instance.py:2291 +#: vrtManager/instance.py:2294 #, python-format msgid "%(error)s; the VM may use %(dest)s now: check its disk %(dev)s" msgstr "" "%(error)s; sanal makine şu anda %(dest)s dosyasını kullanıyor olabilir: " "%(dev)s diskini kontrol edin" -#: vrtManager/instance.py:2298 +#: vrtManager/instance.py:2301 #, python-format msgid "The VM has no internal snapshot named %(name)s" msgstr "Sanal makinenin %(name)s adlı dahili anlık görüntüsü yok" -#: vrtManager/instance.py:2307 +#: vrtManager/instance.py:2310 msgid "The VM has a saved state; start it or remove the saved state first" msgstr "" "Sanal makinenin kaydedilmiş durumu var; önce başlatın veya kaydedilmiş durumu" " kaldırın" -#: vrtManager/instance.py:2309 +#: vrtManager/instance.py:2312 msgid "A snapshot job is still running on this VM; try again when it ends" msgstr "" "Bu sanal makinede hâlâ bir anlık görüntü işi çalışıyor; bittiğinde tekrar " "deneyin" -#: vrtManager/instance.py:2319 +#: vrtManager/instance.py:2322 msgid "Shut the VM down to revert to an internal snapshot" msgstr "Dahili bir anlık görüntüye geri dönmek için sanal makineyi kapatın" -#: vrtManager/instance.py:2417 +#: vrtManager/instance.py:2420 msgid "Cannot clone a VM whose NVRAM is not a file" msgstr "NVRAM'i dosya olmayan bir sanal makine klonlanamaz" -#: vrtManager/instance.py:2485 +#: vrtManager/instance.py:2488 #, python-format msgid "Clone failed (%(err)s); remove these copies by hand: %(path)s" msgstr "" "Klonlama başarısız oldu (%(err)s); bu kopyaları elle kaldırın: %(path)s" -#: vrtManager/instance.py:2495 +#: vrtManager/instance.py:2498 msgid "Shut the VM down before cloning it" msgstr "Klonlamadan önce sanal makineyi kapatın" -#: vrtManager/instance.py:2549 +#: vrtManager/instance.py:2552 #, python-format msgid "Clone failed (%(err)s); remove these copies by hand: %(leftovers)s" msgstr "" "Klonlama başarısız oldu (%(err)s); bu kopyaları elle kaldırın: %(leftovers)s" -#: vrtManager/instance.py:2560 +#: vrtManager/instance.py:2563 msgid "Live clone needs libvirt 11.10 or later; shut the VM down to clone it" msgstr "" "Canlı klonlama libvirt 11.10 veya sonrasını gerektirir; klonlamak için sanal " "makineyi kapatın" -#: vrtManager/instance.py:2563 +#: vrtManager/instance.py:2566 msgid "A VM with a TPM is cloned only shut down" msgstr "TPM'i olan bir sanal makine yalnızca kapalıyken klonlanır" -#: vrtManager/instance.py:2566 +#: vrtManager/instance.py:2569 #, python-format msgid "Disk %(dev)s is not a local file; shut the VM down to clone it" msgstr "" "Disk %(dev)s yerel bir dosya değil; klonlamak için sanal makineyi kapatın" -#: vrtManager/instance.py:2568 +#: vrtManager/instance.py:2571 #, python-format msgid "Disk %(dev)s is shareable; shut the VM down to clone it" msgstr "Disk %(dev)s paylaşılabilir; klonlamak için sanal makineyi kapatın" -#: vrtManager/instance.py:2573 +#: vrtManager/instance.py:2576 #, python-format msgid "Disk %(dev)s changes at the next start; shut the VM down to clone it" msgstr "" "Disk %(dev)s sonraki başlatmada değişiyor; klonlamak için sanal makineyi " "kapatın" -#: vrtManager/instance.py:2575 +#: vrtManager/instance.py:2578 msgid "Another job is running on the VM; clone it when that ends" msgstr "Sanal makinede başka bir iş çalışıyor; o bittiğinde klonlayın" -#: vrtManager/instance.py:2588 +#: vrtManager/instance.py:2591 #, python-format msgid "Volume %(name)s already exists in storage pool %(pool)s" msgstr "%(name)s birimi %(pool)s depolama havuzunda zaten var" -#: vrtManager/instance.py:2607 +#: vrtManager/instance.py:2610 #, python-format msgid "" "Storage pool %(pool)s has %(free).1f GiB free; the clone needs %(size).1f GiB" @@ -9427,20 +9427,20 @@ msgstr "" "gerektiriyor (kopyalanan diskler, artı bunların %%%(percent)g kadarı, en az " "%(minimum)g GiB)" -#: vrtManager/instance.py:2746 +#: vrtManager/instance.py:2749 msgid "A network interface that is a host device is removed in the XML editor" msgstr "Sunucu aygıtı olan bir ağ arabirimi XML düzenleyicide kaldırılır" -#: vrtManager/instance.py:2762 +#: vrtManager/instance.py:2765 #, python-format msgid "No network interface with MAC %(old_mac)s" msgstr "MAC adresi %(old_mac)s olan ağ arabirimi yok" -#: vrtManager/instance.py:2765 +#: vrtManager/instance.py:2768 msgid "A network interface that is a host device is changed in the XML editor" msgstr "Sunucu aygıtı olan bir ağ arabirimi XML düzenleyicide değiştirilir" -#: vrtManager/instance.py:2856 +#: vrtManager/instance.py:2859 msgid "" "A VM changes its PCI devices while it runs, or is shut off without a saved " "state" @@ -9448,14 +9448,14 @@ msgstr "" "Sanal makine PCI aygıtlarını çalışırken veya kaydedilmiş durumu olmadan " "kapalıyken değiştirir" -#: vrtManager/instance.py:2868 +#: vrtManager/instance.py:2871 #, python-format msgid "%(err)s; whether the VM has PCI device %(address)s now is not known" msgstr "" "%(err)s; sanal makinede şu anda %(address)s PCI aygıtının olup olmadığı " "bilinmiyor" -#: vrtManager/instance.py:2870 +#: vrtManager/instance.py:2873 #, python-format msgid "" "%(err)s; PCI device %(address)s: the VM is not running, its next start has it" @@ -9463,7 +9463,7 @@ msgstr "" "%(err)s; PCI aygıtı %(address)s: sanal makine çalışmıyor, sonraki başlatmada " "var" -#: vrtManager/instance.py:2872 +#: vrtManager/instance.py:2875 #, python-format msgid "" "%(err)s; PCI device %(address)s: the VM is not running, its next start does " @@ -9472,7 +9472,7 @@ msgstr "" "%(err)s; PCI aygıtı %(address)s: sanal makine çalışmıyor, sonraki başlatmada " "yok" -#: vrtManager/instance.py:2873 +#: vrtManager/instance.py:2876 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM has it, its next start has it" @@ -9480,7 +9480,7 @@ msgstr "" "%(err)s; PCI aygıtı %(address)s: çalışan sanal makinede var, sonraki " "başlatmada var" -#: vrtManager/instance.py:2875 +#: vrtManager/instance.py:2878 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM has it, its next start does " @@ -9489,7 +9489,7 @@ msgstr "" "%(err)s; PCI aygıtı %(address)s: çalışan sanal makinede var, sonraki " "başlatmada yok" -#: vrtManager/instance.py:2877 +#: vrtManager/instance.py:2880 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM does not have it, its next " @@ -9498,7 +9498,7 @@ msgstr "" "%(err)s; PCI aygıtı %(address)s: çalışan sanal makinede yok, sonraki " "başlatmada var" -#: vrtManager/instance.py:2879 +#: vrtManager/instance.py:2882 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM does not have it, its next " @@ -9507,34 +9507,34 @@ msgstr "" "%(err)s; PCI aygıtı %(address)s: çalışan sanal makinede yok, sonraki " "başlatmada yok" -#: vrtManager/instance.py:2913 +#: vrtManager/instance.py:2916 #, python-format msgid "The VM has no PCI device %(address)s" msgstr "Sanal makinede %(address)s PCI aygıtı yok" -#: vrtManager/instance.py:2931 +#: vrtManager/instance.py:2934 msgid "The VM has no USB controller" msgstr "Sanal makinede USB denetleyicisi yok" -#: vrtManager/instance.py:2950 +#: vrtManager/instance.py:2953 msgid "The VM has no such USB device" msgstr "Sanal makinede böyle bir USB aygıtı yok" -#: vrtManager/instance.py:2964 +#: vrtManager/instance.py:2967 #, python-format msgid "The VM has no network interface %(mac)s" msgstr "Sanal makinede %(mac)s ağ arabirimi yok" -#: vrtManager/instance.py:2995 +#: vrtManager/instance.py:2998 msgid "The VM has its own RNG device: change it in the XML editor" msgstr "" "Sanal makinenin kendi RNG aygıtı var: bunu XML düzenleyicide değiştirin" -#: vrtManager/instance.py:3022 +#: vrtManager/instance.py:3025 msgid "The VM has its own TPM: change it in the XML editor" msgstr "Sanal makinenin kendi TPM'i var: bunu XML düzenleyicide değiştirin" -#: vrtManager/instance.py:3041 +#: vrtManager/instance.py:3044 #, python-format msgid "Unknown crash action %(action)s" msgstr "Bilinmeyen çökme eylemi %(action)s" @@ -9935,6 +9935,13 @@ msgstr "" "%(name)s birimi kullanımda: bir sanal makinenin diski, bir temel (backing) " "dosya ya da bir anlık görüntünün dosyası" +#: vrtManager/storage.py:360 +#, python-format +msgid "The running VMs %(vms)s use volume %(name)s; shut them down to copy it" +msgstr "" +"Çalışan %(vms)s sanal makineleri %(name)s birimini kullanıyor; kopyalamak " +"için onları kapatın" + #: vrtManager/util.py:99 #, python-format msgid "The XML is not valid: %(err)s" diff --git a/locale/zh/LC_MESSAGES/django.mo b/locale/zh/LC_MESSAGES/django.mo index 64d26c98..fcd2dcc7 100644 Binary files a/locale/zh/LC_MESSAGES/django.mo and b/locale/zh/LC_MESSAGES/django.mo differ diff --git a/locale/zh/LC_MESSAGES/django.po b/locale/zh/LC_MESSAGES/django.po index d9d7f778..a9e25472 100644 --- a/locale/zh/LC_MESSAGES/django.po +++ b/locale/zh/LC_MESSAGES/django.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: \n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2026-11-07 19:47+0000\n" +"POT-Creation-Date: 2026-11-07 20:40+0000\n" "PO-Revision-Date: \n" "Last-Translator: \n" "Language-Team: \n" @@ -2693,7 +2693,7 @@ msgstr "虚拟机未定义;请检查这些卷,然后处理此任务:%(volu msgid "Delete snapshot" msgstr "删除快照" -#: instances/jobs.py:317 vrtManager/instance.py:2297 +#: instances/jobs.py:317 vrtManager/instance.py:2300 #, python-format msgid "The VM has no external snapshot named %(name)s" msgstr "虚拟机没有名为 %(name)s 的外部快照" @@ -2725,7 +2725,7 @@ msgstr "虚拟机已不在运行该任务的计算节点上" msgid "Take snapshot" msgstr "创建快照" -#: instances/jobs.py:385 instances/jobs.py:394 vrtManager/instance.py:1893 +#: instances/jobs.py:385 instances/jobs.py:394 vrtManager/instance.py:1896 #, python-format msgid "A snapshot named %(name)s already exists" msgstr "名为 %(name)s 的快照已存在" @@ -2901,7 +2901,7 @@ msgstr "cloud-init 种子需要为磁盘使用目录类型的存储池" msgid "This host offers no firmware %(firmware)s" msgstr "此主机不提供固件 %(firmware)s" -#: instances/jobs.py:838 vrtManager/instance.py:3029 +#: instances/jobs.py:838 vrtManager/instance.py:3032 msgid "This host offers no TPM 2.0: install swtpm on it" msgstr "此主机不提供 TPM 2.0:请在主机上安装 swtpm" @@ -5615,16 +5615,16 @@ msgstr "%(quota)s(%(total)s > %(limit)s)" msgid "None available device name" msgstr "没有可用的设备名称" -#: instances/utils.py:434 +#: instances/utils.py:435 #, python-format msgid "%(hostname)s via %(address)s" msgstr "%(hostname)s,经由 %(address)s" -#: instances/utils.py:473 +#: instances/utils.py:474 msgid "Invalid MAC address" msgstr "无效的 MAC 地址" -#: instances/utils.py:475 +#: instances/utils.py:476 msgid "More MAC addresses than networks" msgstr "MAC 地址数量多于网络数量" @@ -7619,50 +7619,50 @@ msgstr "镜像名称不能超过 120 个字符" msgid "Clone volume" msgstr "克隆卷" -#: storages/jobs.py:59 storages/jobs.py:70 +#: storages/jobs.py:60 storages/jobs.py:73 msgid "Name of volume already in use" msgstr "卷名已被使用" -#: storages/jobs.py:65 +#: storages/jobs.py:67 #, python-format msgid "The pool has no volume named %(name)s" msgstr "存储池中没有名为 %(name)s 的卷" -#: storages/jobs.py:67 +#: storages/jobs.py:69 msgid "An ISO image is not cloned" msgstr "ISO 镜像不会被克隆" -#: storages/jobs.py:79 +#: storages/jobs.py:82 msgid "Copying the volume" msgstr "正在复制卷" -#: storages/jobs.py:91 +#: storages/jobs.py:94 msgid "" "The copy exists, but the job did not see it finish; check it, then resolve " "this job." msgstr "副本已存在,但任务未看到其完成;请检查后处理此任务。" -#: storages/jobs.py:92 +#: storages/jobs.py:95 msgid "The copy was not made" msgstr "未创建副本" -#: storages/jobs.py:103 +#: storages/jobs.py:106 msgid "Upload ISO image" msgstr "上传 ISO 镜像" -#: storages/jobs.py:118 +#: storages/jobs.py:121 msgid "Invalid file name" msgstr "文件名无效" -#: storages/jobs.py:120 +#: storages/jobs.py:123 msgid "Only .iso files can be uploaded" msgstr "只能上传 .iso 文件" -#: storages/jobs.py:122 +#: storages/jobs.py:125 msgid "Invalid file size" msgstr "文件大小无效" -#: storages/jobs.py:124 +#: storages/jobs.py:127 msgid "Invalid chunk index or total chunks" msgstr "分块索引或分块总数无效" @@ -8536,201 +8536,201 @@ msgid "" "file %(file)s" msgstr "%(target)s (%(path)s):目标主机的存储池 %(pool)s 中已有文件 %(file)s" -#: vrtManager/instance.py:375 +#: vrtManager/instance.py:378 #, python-format msgid "%(target)s (%(path)s): another disk is copied to %(dest)s" msgstr "%(target)s (%(path)s):另一个磁盘已复制到 %(dest)s" -#: vrtManager/instance.py:380 +#: vrtManager/instance.py:383 #, python-format msgid "%(target)s: the VM has no disk file to copy" msgstr "%(target)s:虚拟机没有可复制的磁盘文件" -#: vrtManager/instance.py:384 +#: vrtManager/instance.py:387 #, python-format msgid "" "%(target)s (%(path)s) of the next start: the destination host does not share " "it" msgstr "下次启动的 %(target)s (%(path)s):目标主机不共享它" -#: vrtManager/instance.py:388 +#: vrtManager/instance.py:391 #, python-format msgid "The disks cannot be migrated: %(problems)s" msgstr "磁盘无法迁移:%(problems)s" -#: vrtManager/instance.py:401 +#: vrtManager/instance.py:404 #, python-format msgid "" "%(error)s; remove the partial disk copies from the destination host: " "%(copies)s" msgstr "%(error)s;请从目标主机删除不完整的磁盘副本:%(copies)s" -#: vrtManager/instance.py:418 +#: vrtManager/instance.py:421 #, python-format msgid "" "%(error)s; remove the partial disk copies from the destination host: %(left)s" msgstr "%(error)s;请从目标主机删除不完整的磁盘副本:%(left)s" -#: vrtManager/instance.py:432 +#: vrtManager/instance.py:435 #, python-format msgid "" "The NVRAM file %(path)s is not in libvirt's NVRAM directory %(dir)s and " "cannot be copied" msgstr "NVRAM 文件 %(path)s 不在 libvirt 的 NVRAM 目录 %(dir)s 中,无法复制" -#: vrtManager/instance.py:441 +#: vrtManager/instance.py:444 #, python-format msgid "The destination host cannot see the NVRAM file %(path)s" msgstr "目标主机看不到 NVRAM 文件 %(path)s" -#: vrtManager/instance.py:517 +#: vrtManager/instance.py:520 #, python-format msgid "%(type)s disk, cannot be checked" msgstr "%(type)s 磁盘,无法检查" -#: vrtManager/instance.py:557 +#: vrtManager/instance.py:560 #, python-format msgid "The destination host already has a VM %(key)s" msgstr "目标主机上已有虚拟机 %(key)s" -#: vrtManager/instance.py:579 +#: vrtManager/instance.py:582 msgid "The VM was started on the source host during the migration" msgstr "迁移期间虚拟机在源主机上被启动" -#: vrtManager/instance.py:595 +#: vrtManager/instance.py:598 #, python-format msgid "" "%(error)s; the VM may now be defined only on the destination host: check both" " hosts" msgstr "%(error)s;虚拟机现在可能只在目标主机上定义:请检查两台主机" -#: vrtManager/instance.py:601 +#: vrtManager/instance.py:604 #, python-format msgid "" "%(error)s; the VM is now defined on both hosts, remove it from the " "destination: %(undo_error)s" msgstr "%(error)s;虚拟机现在在两台主机上都有定义,请从目标主机删除它:%(undo_error)s" -#: vrtManager/instance.py:607 +#: vrtManager/instance.py:610 msgid "" "Snapshot names are 1-64 letters, digits, '.', '_' or '-' and do not start " "with '.'" msgstr "快照名称为 1-64 个字母、数字、'.'、'_' 或 '-',且不能以 '.' 开头" -#: vrtManager/instance.py:1095 +#: vrtManager/instance.py:1098 msgid "" "A device other than a disk or NIC is in the boot order: change it in the XML " "editor" msgstr "启动顺序中有磁盘或网卡以外的设备:请在 XML 编辑器中修改" -#: vrtManager/instance.py:1107 +#: vrtManager/instance.py:1110 msgid "Invalid Device Type for boot order" msgstr "启动顺序的设备类型无效" -#: vrtManager/instance.py:1110 +#: vrtManager/instance.py:1113 #, python-format msgid "Boot device %(dev)s is not in the definition" msgstr "启动设备 %(dev)s 不在定义中" -#: vrtManager/instance.py:1130 +#: vrtManager/instance.py:1133 #, python-format msgid "CD-ROM %(dev)s is not in the running definition" msgstr "CD-ROM %(dev)s 不在运行中的定义中" -#: vrtManager/instance.py:1131 +#: vrtManager/instance.py:1134 #, python-format msgid "CD-ROM %(dev)s is not in the persistent definition" msgstr "CD-ROM %(dev)s 不在持久定义中" -#: vrtManager/instance.py:1143 +#: vrtManager/instance.py:1146 #, python-format msgid "Media of %(dev)s changed in the running VM only: %(err)s" msgstr "%(dev)s 的介质仅在运行中的虚拟机中更改:%(err)s" -#: vrtManager/instance.py:1154 +#: vrtManager/instance.py:1157 #, python-format msgid "ISO image %(image)s was not found" msgstr "未找到 ISO 镜像 %(image)s" -#: vrtManager/instance.py:1156 +#: vrtManager/instance.py:1159 #, python-format msgid "ISO image %(image)s is in more than one storage pool" msgstr "ISO 镜像 %(image)s 位于多个存储池中" -#: vrtManager/instance.py:1263 +#: vrtManager/instance.py:1266 #, python-format msgid "Disk %(target_dev)s is not in the VM's definition" msgstr "磁盘 %(target_dev)s 不在虚拟机的定义中" -#: vrtManager/instance.py:1391 +#: vrtManager/instance.py:1394 msgid "Please shutdown the instance then try to enable vCPU hotplug" msgstr "请先关闭虚拟机,再启用 vCPU 热插拔" -#: vrtManager/instance.py:1678 +#: vrtManager/instance.py:1681 msgid "The VM has no video card" msgstr "虚拟机没有显卡" -#: vrtManager/instance.py:1852 +#: vrtManager/instance.py:1855 msgid "" "The VM has external snapshots; internal snapshots cannot be mixed with them" msgstr "虚拟机有外部快照;内部快照不能与其混用" -#: vrtManager/instance.py:1884 +#: vrtManager/instance.py:1887 msgid "A snapshot with memory is not quiesced; it keeps the whole guest state" msgstr "含内存的快照不会静默文件系统;它保存整个客户机状态" -#: vrtManager/instance.py:1886 +#: vrtManager/instance.py:1889 msgid "Only a running VM's file systems can be frozen" msgstr "只有运行中的虚拟机的文件系统可以冻结" -#: vrtManager/instance.py:1888 +#: vrtManager/instance.py:1891 msgid "The QEMU guest agent is not connected; it freezes the file systems" msgstr "QEMU 客户机代理未连接;文件系统由它冻结" -#: vrtManager/instance.py:1891 +#: vrtManager/instance.py:1894 msgid "" "The VM has internal snapshots; external snapshots cannot be mixed with them" msgstr "虚拟机有内部快照;外部快照不能与其混用" -#: vrtManager/instance.py:1896 +#: vrtManager/instance.py:1899 msgid "Newer snapshots exist after the last revert; delete them first" msgstr "上次还原后存在更新的快照;请先删除它们" -#: vrtManager/instance.py:1899 +#: vrtManager/instance.py:1902 msgid "No snapshot is current; revert to a snapshot first" msgstr "没有当前快照;请先还原到某个快照" -#: vrtManager/instance.py:1905 +#: vrtManager/instance.py:1908 #, python-format msgid "Eject the media from %(dev)s first" msgstr "请先弹出 %(dev)s 中的介质" -#: vrtManager/instance.py:1907 +#: vrtManager/instance.py:1910 #, python-format msgid "Disk %(dev)s is not a file; external snapshots need file disks" msgstr "磁盘 %(dev)s 不是文件;外部快照需要文件磁盘" -#: vrtManager/instance.py:1915 +#: vrtManager/instance.py:1918 #, python-format msgid "" "The storage pools could not be refreshed, so their free space is unknown: " "%(err)s" msgstr "无法刷新存储池,其可用空间未知:%(err)s" -#: vrtManager/instance.py:1936 +#: vrtManager/instance.py:1939 msgid "Memory is saved only from a running VM" msgstr "只能保存运行中的虚拟机的内存" -#: vrtManager/instance.py:1938 +#: vrtManager/instance.py:1941 msgid "The VM has no disk to keep its memory next to" msgstr "虚拟机没有可存放其内存的磁盘" -#: vrtManager/instance.py:1942 +#: vrtManager/instance.py:1945 #, python-format msgid "%(disk)s is not in a storage pool; memory is saved only into one" msgstr "%(disk)s 不在存储池中;内存只能保存到存储池中" -#: vrtManager/instance.py:1973 +#: vrtManager/instance.py:1976 #, python-format msgid "" "Storage pool %(pool)s has %(free).1f GiB free; the snapshot needs %(size).1f " @@ -8740,156 +8740,156 @@ msgstr "" "存储池 %(pool)s 可用 %(free).1f GiB;快照需要 %(size).1f GiB(其中虚拟机磁盘的 %(percent)g%%,至少 " "%(minimum)g GiB,若保存内存则另加内存)" -#: vrtManager/instance.py:1991 +#: vrtManager/instance.py:1994 msgid "" "This snapshot was taken by an older version on a UEFI VM and cannot be " "reverted; delete it instead" msgstr "此快照由旧版本在 UEFI 虚拟机上创建,无法还原;请将其删除" -#: vrtManager/instance.py:2021 +#: vrtManager/instance.py:2024 #, python-format msgid "" "The revert failed twice; try again in a moment (%(error)s). The VM is " "running." msgstr "还原两次失败;请稍后重试(%(error)s)。虚拟机正在运行。" -#: vrtManager/instance.py:2023 +#: vrtManager/instance.py:2026 #, python-format msgid "" "The revert failed twice; try again in a moment (%(error)s). The VM is shut " "off." msgstr "还原两次失败;请稍后重试(%(error)s)。虚拟机已关机。" -#: vrtManager/instance.py:2186 +#: vrtManager/instance.py:2189 msgid "A disk moves when its VM is defined and running, paused or shut off" msgstr "仅当虚拟机已定义且处于运行、暂停或关机状态时才能移动磁盘" -#: vrtManager/instance.py:2188 +#: vrtManager/instance.py:2191 msgid "" "A disk of a VM with snapshots, a saved state or a running block job does not " "move" msgstr "有快照、保存的状态或正在运行块任务的虚拟机的磁盘不能移动" -#: vrtManager/instance.py:2196 +#: vrtManager/instance.py:2199 #, python-format msgid "" "%(dev)s is not a disk file of the VM, the same in its running and next " "start's definition" msgstr "%(dev)s 不是该虚拟机在运行中的定义和下次启动定义中相同的磁盘文件" -#: vrtManager/instance.py:2201 +#: vrtManager/instance.py:2204 #, python-format msgid "%(dev)s does not move: only writable raw and qcow2 disks do" msgstr "%(dev)s 不能移动:只能移动可写的 raw 和 qcow2 磁盘" -#: vrtManager/instance.py:2208 +#: vrtManager/instance.py:2211 #, python-format msgid "%(dev)s does not move: no storage pool has %(path)s" msgstr "%(dev)s 不能移动:没有存储池包含 %(path)s" -#: vrtManager/instance.py:2210 +#: vrtManager/instance.py:2213 #, python-format msgid "%(dev)s does not move: it has a backing file" msgstr "%(dev)s 不能移动:它有后备文件" -#: vrtManager/instance.py:2213 +#: vrtManager/instance.py:2216 #, python-format msgid "%(pool_name)s is not an active pool of disk files of this host" msgstr "%(pool_name)s 不是此主机上活动的磁盘文件存储池" -#: vrtManager/instance.py:2216 +#: vrtManager/instance.py:2219 #, python-format msgid "%(dev)s is in pool %(pool_name)s already" msgstr "%(dev)s 已在存储池 %(pool_name)s 中" -#: vrtManager/instance.py:2220 +#: vrtManager/instance.py:2223 #, python-format msgid "Pool %(pool_name)s already has a file %(name)s" msgstr "存储池 %(pool_name)s 中已有文件 %(name)s" -#: vrtManager/instance.py:2244 +#: vrtManager/instance.py:2247 #, python-format msgid "The copy of %(dev)s ended before it was complete" msgstr "%(dev)s 的复制在完成前结束" -#: vrtManager/instance.py:2289 +#: vrtManager/instance.py:2292 #, python-format msgid "%(error)s; remove %(dest)s if it is there: %(cleanup_error)s" msgstr "%(error)s;如果 %(dest)s 存在请将其删除:%(cleanup_error)s" -#: vrtManager/instance.py:2291 +#: vrtManager/instance.py:2294 #, python-format msgid "%(error)s; the VM may use %(dest)s now: check its disk %(dev)s" msgstr "%(error)s;虚拟机现在可能在使用 %(dest)s:请检查其磁盘 %(dev)s" -#: vrtManager/instance.py:2298 +#: vrtManager/instance.py:2301 #, python-format msgid "The VM has no internal snapshot named %(name)s" msgstr "虚拟机没有名为 %(name)s 的内部快照" -#: vrtManager/instance.py:2307 +#: vrtManager/instance.py:2310 msgid "The VM has a saved state; start it or remove the saved state first" msgstr "虚拟机有保存的状态;请先启动它或删除保存的状态" -#: vrtManager/instance.py:2309 +#: vrtManager/instance.py:2312 msgid "A snapshot job is still running on this VM; try again when it ends" msgstr "此虚拟机上仍有快照任务在运行;请在其结束后重试" -#: vrtManager/instance.py:2319 +#: vrtManager/instance.py:2322 msgid "Shut the VM down to revert to an internal snapshot" msgstr "请关闭虚拟机后再还原到内部快照" -#: vrtManager/instance.py:2417 +#: vrtManager/instance.py:2420 msgid "Cannot clone a VM whose NVRAM is not a file" msgstr "NVRAM 不是文件的虚拟机无法克隆" -#: vrtManager/instance.py:2485 +#: vrtManager/instance.py:2488 #, python-format msgid "Clone failed (%(err)s); remove these copies by hand: %(path)s" msgstr "克隆失败(%(err)s);请手动删除这些副本:%(path)s" -#: vrtManager/instance.py:2495 +#: vrtManager/instance.py:2498 msgid "Shut the VM down before cloning it" msgstr "请先关闭虚拟机再克隆" -#: vrtManager/instance.py:2549 +#: vrtManager/instance.py:2552 #, python-format msgid "Clone failed (%(err)s); remove these copies by hand: %(leftovers)s" msgstr "克隆失败(%(err)s);请手动删除这些副本:%(leftovers)s" -#: vrtManager/instance.py:2560 +#: vrtManager/instance.py:2563 msgid "Live clone needs libvirt 11.10 or later; shut the VM down to clone it" msgstr "在线克隆需要 libvirt 11.10 或更高版本;请关闭虚拟机后再克隆" -#: vrtManager/instance.py:2563 +#: vrtManager/instance.py:2566 msgid "A VM with a TPM is cloned only shut down" msgstr "带 TPM 的虚拟机只能在关机时克隆" -#: vrtManager/instance.py:2566 +#: vrtManager/instance.py:2569 #, python-format msgid "Disk %(dev)s is not a local file; shut the VM down to clone it" msgstr "磁盘 %(dev)s 不是本地文件;请关闭虚拟机后再克隆" -#: vrtManager/instance.py:2568 +#: vrtManager/instance.py:2571 #, python-format msgid "Disk %(dev)s is shareable; shut the VM down to clone it" msgstr "磁盘 %(dev)s 是可共享的;请关闭虚拟机后再克隆" -#: vrtManager/instance.py:2573 +#: vrtManager/instance.py:2576 #, python-format msgid "Disk %(dev)s changes at the next start; shut the VM down to clone it" msgstr "磁盘 %(dev)s 在下次启动时会改变;请关闭虚拟机后再克隆" -#: vrtManager/instance.py:2575 +#: vrtManager/instance.py:2578 msgid "Another job is running on the VM; clone it when that ends" msgstr "虚拟机上有另一个任务正在运行;请在其结束后再克隆" -#: vrtManager/instance.py:2588 +#: vrtManager/instance.py:2591 #, python-format msgid "Volume %(name)s already exists in storage pool %(pool)s" msgstr "卷 %(name)s 已存在于存储池 %(pool)s 中" -#: vrtManager/instance.py:2607 +#: vrtManager/instance.py:2610 #, python-format msgid "" "Storage pool %(pool)s has %(free).1f GiB free; the clone needs %(size).1f GiB" @@ -8898,97 +8898,97 @@ msgstr "" "存储池 %(pool)s 可用 %(free).1f GiB;克隆需要 %(size).1f GiB(复制的磁盘,再加其 %(percent)g%%,至少" " %(minimum)g GiB)" -#: vrtManager/instance.py:2746 +#: vrtManager/instance.py:2749 msgid "A network interface that is a host device is removed in the XML editor" msgstr "作为主机设备的网络接口需在 XML 编辑器中删除" -#: vrtManager/instance.py:2762 +#: vrtManager/instance.py:2765 #, python-format msgid "No network interface with MAC %(old_mac)s" msgstr "没有 MAC 为 %(old_mac)s 的网络接口" -#: vrtManager/instance.py:2765 +#: vrtManager/instance.py:2768 msgid "A network interface that is a host device is changed in the XML editor" msgstr "作为主机设备的网络接口需在 XML 编辑器中修改" -#: vrtManager/instance.py:2856 +#: vrtManager/instance.py:2859 msgid "" "A VM changes its PCI devices while it runs, or is shut off without a saved " "state" msgstr "虚拟机只能在运行时或无保存的状态的关机时更改其 PCI 设备" -#: vrtManager/instance.py:2868 +#: vrtManager/instance.py:2871 #, python-format msgid "%(err)s; whether the VM has PCI device %(address)s now is not known" msgstr "%(err)s;虚拟机现在是否有 PCI 设备 %(address)s 未知" -#: vrtManager/instance.py:2870 +#: vrtManager/instance.py:2873 #, python-format msgid "" "%(err)s; PCI device %(address)s: the VM is not running, its next start has it" msgstr "%(err)s;PCI 设备 %(address)s:虚拟机未运行,下次启动时有它" -#: vrtManager/instance.py:2872 +#: vrtManager/instance.py:2875 #, python-format msgid "" "%(err)s; PCI device %(address)s: the VM is not running, its next start does " "not have it" msgstr "%(err)s;PCI 设备 %(address)s:虚拟机未运行,下次启动时没有它" -#: vrtManager/instance.py:2873 +#: vrtManager/instance.py:2876 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM has it, its next start has it" msgstr "%(err)s;PCI 设备 %(address)s:运行中的虚拟机有它,下次启动时有它" -#: vrtManager/instance.py:2875 +#: vrtManager/instance.py:2878 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM has it, its next start does " "not have it" msgstr "%(err)s;PCI 设备 %(address)s:运行中的虚拟机有它,下次启动时没有它" -#: vrtManager/instance.py:2877 +#: vrtManager/instance.py:2880 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM does not have it, its next " "start has it" msgstr "%(err)s;PCI 设备 %(address)s:运行中的虚拟机没有它,下次启动时有它" -#: vrtManager/instance.py:2879 +#: vrtManager/instance.py:2882 #, python-format msgid "" "%(err)s; PCI device %(address)s: the running VM does not have it, its next " "start does not have it" msgstr "%(err)s;PCI 设备 %(address)s:运行中的虚拟机没有它,下次启动时没有它" -#: vrtManager/instance.py:2913 +#: vrtManager/instance.py:2916 #, python-format msgid "The VM has no PCI device %(address)s" msgstr "虚拟机没有 PCI 设备 %(address)s" -#: vrtManager/instance.py:2931 +#: vrtManager/instance.py:2934 msgid "The VM has no USB controller" msgstr "虚拟机没有 USB 控制器" -#: vrtManager/instance.py:2950 +#: vrtManager/instance.py:2953 msgid "The VM has no such USB device" msgstr "虚拟机没有此 USB 设备" -#: vrtManager/instance.py:2964 +#: vrtManager/instance.py:2967 #, python-format msgid "The VM has no network interface %(mac)s" msgstr "虚拟机没有网络接口 %(mac)s" -#: vrtManager/instance.py:2995 +#: vrtManager/instance.py:2998 msgid "The VM has its own RNG device: change it in the XML editor" msgstr "虚拟机有自己的 RNG 设备:请在 XML 编辑器中修改" -#: vrtManager/instance.py:3022 +#: vrtManager/instance.py:3025 msgid "The VM has its own TPM: change it in the XML editor" msgstr "虚拟机有自己的 TPM:请在 XML 编辑器中修改" -#: vrtManager/instance.py:3041 +#: vrtManager/instance.py:3044 #, python-format msgid "Unknown crash action %(action)s" msgstr "未知的崩溃操作 %(action)s" @@ -9361,6 +9361,11 @@ msgid "" "Volume %(name)s is in use: a VM's disk, a backing file or a snapshot's file" msgstr "卷 %(name)s 正在使用中:它是虚拟机的磁盘、后备文件或快照文件" +#: vrtManager/storage.py:360 +#, python-format +msgid "The running VMs %(vms)s use volume %(name)s; shut them down to copy it" +msgstr "正在运行的虚拟机 %(vms)s 使用卷 %(name)s;请先将其关闭再复制" + #: vrtManager/util.py:99 #, python-format msgid "The XML is not valid: %(err)s" diff --git a/storages/jobs.py b/storages/jobs.py index 3b930f46..71404c00 100644 --- a/storages/jobs.py +++ b/storages/jobs.py @@ -55,8 +55,10 @@ class CloneVolume(Kind): if op.user is None or not op.user.is_active or not op.user.is_superuser: raise PermissionDenied # a volume made outside the panel since the job was queued may have taken the name - if op.intent["target"] in _storage(op.params)[1].get_volumes(): + stg = _storage(op.params)[1] + if op.intent["target"] in stg.get_volumes(): raise util.OperationError(gettext_noop("Name of volume already in use")) + stg.refuse_running_copy(op.params["image"]) # the VM may have started since def plan(self, user, params): compute, stg = _storage(params) @@ -65,6 +67,7 @@ class CloneVolume(Kind): raise util.OperationError(gettext_noop("The pool has no volume named %(name)s"), name=params["image"]) if is_iso(params["image"]): raise util.OperationError(gettext_noop("An ISO image is not cloned")) + stg.refuse_running_copy(params["image"]) target = stg.clone_name(params["name"], params["format"] or stg.get_volume_format_type(params["image"])) if target in volumes: raise util.OperationError(gettext_noop("Name of volume already in use")) diff --git a/storages/tests/test_volume_clone_job.py b/storages/tests/test_volume_clone_job.py index 247bcc17..e89329ed 100644 --- a/storages/tests/test_volume_clone_job.py +++ b/storages/tests/test_volume_clone_job.py @@ -13,6 +13,7 @@ from operations.jobs import Context from operations.models import Claim, Operation, acquire from libvirt import libvirtError from storages.jobs import CloneVolume +from vrtManager import util class VolumeCloneJobTestCase(TransactionTestCase): @@ -64,6 +65,12 @@ class VolumeCloneJobTestCase(TransactionTestCase): response = self.client.post(url, {"cln_volume": "1", "image": image, "name": "copy", "submission_key": key}, follow=True) self.assertContains(response, why) + # a running guest's disk would be copied while it writes + self.stg.get_volumes.return_value = ["base.qcow2"] + self.stg.refuse_running_copy.side_effect = util.OperationError("The running VMs vm use volume base.qcow2") + response = self.client.post(url, {"cln_volume": "1", "image": "base.qcow2", "name": "copy", + "submission_key": "key-vol00004"}, follow=True) + self.assertContains(response, "The running VMs vm use volume base.qcow2") self.assertFalse(Operation.objects.exists()) def test_recovery(self): diff --git a/vrtManager/storage.py b/vrtManager/storage.py index eebd28dd..e75c8a9a 100644 --- a/vrtManager/storage.py +++ b/vrtManager/storage.py @@ -351,6 +351,16 @@ class wvmStorage(wvmConnect): return f"{target_file}.{vol_fmt}" return f"{target_file}.{file_suffix}" if file_suffix else target_file + def refuse_running_copy(self, name): + """A volume a running guest writes is not copied: the copy would mix + instants.""" + path, pool = self.get_volume(name).path(), self.pool.name() + # a disk names it by its path (an RBD image by pool/image) or by its pool and name + uses = "devices/disk/source[@file=$p or @dev=$p or @name=$p or (@pool=$pool and @volume=$v)]" + if vms := self.domains_using(lambda domain: domain.xpath(uses, p=path, pool=pool, v=name), running_only=True): + raise util.OperationError(gettext_noop("The running VMs %(vms)s use volume %(name)s; shut them down to copy it"), + vms=", ".join(vms), name=name) + def clone_volume( self, name, diff --git a/vrtManager/tests/test_volume_in_use.py b/vrtManager/tests/test_volume_in_use.py index 1e8c461f..8a5ed983 100644 --- a/vrtManager/tests/test_volume_in_use.py +++ b/vrtManager/tests/test_volume_in_use.py @@ -132,3 +132,24 @@ class DeleteVolumeTestCase(unittest.TestCase): conn, vols = storage([domain("u1", ["/pool/other.qcow2"])], [volume("/pool/disk.qcow2")]) conn.del_volume("disk.qcow2") vols["disk.qcow2"].delete.assert_called_once_with(0) + + +class RunningCopyTestCase(unittest.TestCase): + """A running guest's disk is not copied: the copy would mix instants.""" + + def test_each_way_a_disk_names_the_volume_refuses_its_copy(self): + for source in ("file='/pool/disk.qcow2'", "dev='/pool/disk.qcow2'", "protocol='rbd' name='/pool/disk.qcow2'", + "pool='pool' volume='disk.qcow2'"): + with self.subTest(source=source): + dom = MagicMock(**{"name.return_value": "vm"}) + dom.XMLDesc.return_value = f"" + conn, _ = storage([dom], [volume("/pool/disk.qcow2")]) + conn.pool.name.return_value = "pool" + with self.assertRaisesRegex(util.OperationError, "The running VMs vm use volume disk.qcow2"): + conn.refuse_running_copy("disk.qcow2") + conn.wvm.listAllDomains.assert_called_once_with(libvirt.VIR_CONNECT_LIST_DOMAINS_ACTIVE) + + def test_another_disk_does_not(self): + conn, _ = storage([domain("u1", ["/pool/other.qcow2"])], [volume("/pool/disk.qcow2")]) + conn.pool.name.return_value = "pool" + conn.refuse_running_copy("disk.qcow2")