fix(vm/import): make the UI respond instantly to .ova file drop (#5274)

When dropping a file on the import zone, the UI didn't acknowledge the file until the vmdk table were parsed.

Now the UI parses the XML instantly, displays it on the UI, and start parsing the tables in the background. If the user clicks the "import" button, the system will finish parsing the tables and start the upload in when fell swoop. Hiding the parsing time in the upload time.
This commit is contained in:
Nicolas Raynaud 2020-09-27 19:45:32 +02:00 committed by GitHub
parent fdbe84cb1e
commit f3527a44d7
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 24 additions and 11 deletions

View File

@ -20,6 +20,7 @@
- [Import VMDK] Fix `No position specified for vmdisk1` error (PR [#5255](https://github.com/vatesfr/xen-orchestra/pull/5255))
- [API] Fix `this.removeSubjectFromResourceSet is not a function` error on calling `resourceSet.removeSubject` via `xo-cli` [#5265](https://github.com/vatesfr/xen-orchestra/issues/5265) (PR [#5266](https://github.com/vatesfr/xen-orchestra/pull/5266))
- [Import OVA] Fix frozen UI when dropping a big OVA on the page (PR [#5274](https://github.com/vatesfr/xen-orchestra/pull/5274))
### Packages to release

View File

@ -79,6 +79,9 @@ test('An ova file is parsed correctly', async () => {
return Buffer.from(buffer).toString(encoder)
}
)
for (const fileName in data.tables) {
data.tables[fileName] = await data.tables[fileName]
}
expect(data).toEqual(expectedResult)
})

View File

@ -5,6 +5,7 @@ import sum from 'lodash/sum'
import xml2js, { processors } from 'xml2js'
import { readVmdkGrainTable } from '.'
import { suppressUnhandledRejection } from './util'
/********
*
@ -327,7 +328,9 @@ export async function parseOVAFile(
const fileSlice = parsableFile.slice(offset, offset + header.fileSize)
const readFile = async (start, end) =>
fileSlice.slice(start, end).read()
data.tables[header.fileName] = await readVmdkGrainTable(readFile)
data.tables[header.fileName] = suppressUnhandledRejection(
readVmdkGrainTable(readFile)
)
}
}
if (!skipVmdk && header.fileName.toLowerCase().endsWith('.vmdk.gz')) {
@ -342,7 +345,9 @@ export async function parseOVAFile(
return parseGzipFromEnd(start, end, fileSlice, header)
}
}
data.tables[header.fileName] = await readVmdkGrainTable(readFile)
data.tables[header.fileName] = suppressUnhandledRejection(
readVmdkGrainTable(readFile)
)
}
offset += Math.ceil(header.fileSize / 512) * 512
}

View File

@ -0,0 +1,4 @@
export function suppressUnhandledRejection(p) {
p.catch(Function.prototype)
return p
}

View File

@ -1,3 +1,5 @@
import { suppressUnhandledRejection } from './util'
const SECTOR_SIZE = 512
const HEADER_SIZE = 512
const FOOTER_POSITION = -1024
@ -138,5 +140,8 @@ export async function readCapacityAndGrainTable(fileAccessor) {
return { grainLogicalAddressList: fragmentAddressList, grainFileOffsetList }
}
return { tablePromise: readTable(), capacityBytes: capacity }
return {
tablePromise: suppressUnhandledRejection(readTable()),
capacityBytes: capacity,
}
}

View File

@ -21,14 +21,9 @@ class BrowserParsableFile extends ParsableFile {
}
async function parseTarFile(file) {
document.body.style.cursor = 'wait'
try {
return parseOVAFile(new BrowserParsableFile(file), (buffer, encoding) =>
return await parseOVAFile(new BrowserParsableFile(file), (buffer, encoding) =>
new TextDecoder(encoding).decode(buffer)
)
} finally {
document.body.style.cursor = null
}
}
export { parseTarFile as default }