@xen-orchestra/backups 0.73.3 → 0.73.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/_incrementalVm.mjs +41 -4
- package/_runners/VmsXapi.mjs +16 -5
- package/package.json +2 -2
package/_incrementalVm.mjs
CHANGED
|
@@ -16,6 +16,44 @@ import { toQcow2Stream } from '@xen-orchestra/qcow2'
|
|
|
16
16
|
|
|
17
17
|
const ensureArray = value => (value === undefined ? [] : Array.isArray(value) ? value : [value])
|
|
18
18
|
|
|
19
|
+
const orderedMemoryLimits = ['memory_static_min', 'memory_dynamic_min', 'memory_dynamic_max', 'memory_static_max']
|
|
20
|
+
|
|
21
|
+
// The dynamic memory range MUST respect this inequality at any moment: static_min <= dynamic_min <= dynamic_max <= static_max.
|
|
22
|
+
// We must update these properties in the right order to avoid XAPI error.
|
|
23
|
+
// The order depends on the values. It can be an increase, a decrease or a mix of both, so any order could be required.
|
|
24
|
+
export async function updateMemoryFields(xapi, targetVm, vmRecord) {
|
|
25
|
+
const memoryValues = {}
|
|
26
|
+
for (const key of orderedMemoryLimits) {
|
|
27
|
+
memoryValues[key] = {
|
|
28
|
+
currentValue: targetVm[key],
|
|
29
|
+
newValue: vmRecord[key] ?? targetVm[key],
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
while (await updateNextMemoryField(xapi, memoryValues, targetVm.$ref)) {
|
|
34
|
+
/* execute until all memory fields are updated */
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
// Update one more memory field if needed, then return a boolean describing if a field was updated or if all fields are up to date
|
|
39
|
+
async function updateNextMemoryField(xapi, memoryValues, vmRef) {
|
|
40
|
+
for (let i = 0; i < orderedMemoryLimits.length; i++) {
|
|
41
|
+
const currentField = memoryValues[orderedMemoryLimits[i]]
|
|
42
|
+
const nextField = i === orderedMemoryLimits.length - 1 ? undefined : memoryValues[orderedMemoryLimits[i + 1]]
|
|
43
|
+
if (
|
|
44
|
+
currentField.newValue !== currentField.currentValue &&
|
|
45
|
+
(nextField === undefined || currentField.newValue <= nextField.currentValue)
|
|
46
|
+
) {
|
|
47
|
+
// no need to check that previousField.currentValue <= currentField.newValue, as we can deduce it
|
|
48
|
+
await xapi.setField('VM', vmRef, orderedMemoryLimits[i], currentField.newValue)
|
|
49
|
+
await xapi.barrier()
|
|
50
|
+
currentField.currentValue = currentField.newValue
|
|
51
|
+
return true
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
return false
|
|
55
|
+
}
|
|
56
|
+
|
|
19
57
|
export async function exportIncrementalVm(
|
|
20
58
|
vm,
|
|
21
59
|
baseVdis = {},
|
|
@@ -160,6 +198,9 @@ export const importIncrementalVm = defer(async function importIncrementalVm(
|
|
|
160
198
|
let vmRef
|
|
161
199
|
if (isUpdate) {
|
|
162
200
|
vmRef = targetRef
|
|
201
|
+
|
|
202
|
+
await updateMemoryFields(xapi, targetVm, vmRecord)
|
|
203
|
+
|
|
163
204
|
await Promise.all([
|
|
164
205
|
xapi.setFields('VM', vmRef, {
|
|
165
206
|
actions_after_crash: vmRecord.actions_after_crash,
|
|
@@ -171,10 +212,6 @@ export const importIncrementalVm = defer(async function importIncrementalVm(
|
|
|
171
212
|
HVM_boot_params: vmRecord.HVM_boot_params,
|
|
172
213
|
HVM_boot_policy: vmRecord.HVM_boot_policy,
|
|
173
214
|
HVM_shadow_multiplier: vmRecord.HVM_shadow_multiplier,
|
|
174
|
-
memory_dynamic_max: vmRecord.memory_dynamic_max,
|
|
175
|
-
memory_dynamic_min: vmRecord.memory_dynamic_min,
|
|
176
|
-
memory_static_max: vmRecord.memory_static_max,
|
|
177
|
-
memory_static_min: vmRecord.memory_static_min,
|
|
178
215
|
name_label: vmRecord.name_label,
|
|
179
216
|
name_description: vmRecord.name_description,
|
|
180
217
|
order: vmRecord.order,
|
package/_runners/VmsXapi.mjs
CHANGED
|
@@ -101,10 +101,14 @@ export const VmsXapi = class VmsXapiBackupRunner extends Abstract {
|
|
|
101
101
|
|
|
102
102
|
const handleVm = vmUuid => {
|
|
103
103
|
const getVmTask = () => {
|
|
104
|
-
|
|
104
|
+
const started = taskByVmId[vmUuid] !== undefined
|
|
105
|
+
if (!started) {
|
|
105
106
|
taskByVmId[vmUuid] = new Task(taskStart)
|
|
106
107
|
}
|
|
107
|
-
return
|
|
108
|
+
return {
|
|
109
|
+
task: taskByVmId[vmUuid],
|
|
110
|
+
started,
|
|
111
|
+
}
|
|
108
112
|
}
|
|
109
113
|
const vmBackupFailed = async (error, task) => {
|
|
110
114
|
if (isLastRun) {
|
|
@@ -135,7 +139,7 @@ export const VmsXapi = class VmsXapiBackupRunner extends Abstract {
|
|
|
135
139
|
taskStart.properties.name_label = vm.name_label
|
|
136
140
|
}
|
|
137
141
|
|
|
138
|
-
const task = getVmTask()
|
|
142
|
+
const { task } = getVmTask()
|
|
139
143
|
// error has to be caught in the task to prevent its failure, but handled outside the task to execute another task.run()
|
|
140
144
|
let taskError
|
|
141
145
|
return task
|
|
@@ -174,12 +178,19 @@ export const VmsXapi = class VmsXapiBackupRunner extends Abstract {
|
|
|
174
178
|
task.success(result)
|
|
175
179
|
} else {
|
|
176
180
|
// ending the task with error or not ending the task
|
|
177
|
-
vmBackupFailed(taskError, task)
|
|
181
|
+
return vmBackupFailed(taskError, task)
|
|
178
182
|
}
|
|
179
183
|
})
|
|
180
184
|
.catch(noop) // errors are handled by logs
|
|
181
185
|
}),
|
|
182
|
-
error =>
|
|
186
|
+
error => {
|
|
187
|
+
const { task: vmTask, started } = getVmTask()
|
|
188
|
+
if (!started) {
|
|
189
|
+
// the task is not started (except if it's a retry), and an unstarted task can't be failed
|
|
190
|
+
vmTask.start()
|
|
191
|
+
}
|
|
192
|
+
return vmBackupFailed(error, vmTask)
|
|
193
|
+
}
|
|
183
194
|
)
|
|
184
195
|
}
|
|
185
196
|
const { concurrency } = settings
|
package/package.json
CHANGED
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
"type": "git",
|
|
9
9
|
"url": "https://github.com/vatesfr/xen-orchestra.git"
|
|
10
10
|
},
|
|
11
|
-
"version": "0.73.
|
|
11
|
+
"version": "0.73.5",
|
|
12
12
|
"engines": {
|
|
13
13
|
"node": ">=14.18"
|
|
14
14
|
},
|
|
@@ -30,7 +30,7 @@
|
|
|
30
30
|
"@vates/nbd-client": "^3.4.0",
|
|
31
31
|
"@vates/parse-duration": "^0.1.1",
|
|
32
32
|
"@vates/task": "^0.7.0",
|
|
33
|
-
"@vates/types": "^1.
|
|
33
|
+
"@vates/types": "^1.28.0",
|
|
34
34
|
"@xen-orchestra/async-map": "^0.1.3",
|
|
35
35
|
"@xen-orchestra/disk-transform": "^1.3.1",
|
|
36
36
|
"@xen-orchestra/fs": "^4.9.1",
|