Read listAll results as rows, not as a response

listAll goes through fetchAllPages, which pages past the server's 100-row cap
and returns the rows themselves. Three asset forms read .data.data off that
array. An array has no .data, so the second access threw and the surrounding
Promise.all rejected, taking the whole load into the catch.

On the PC edit page the throw landed before the record fetch, so no request was
made for the computer at all. The form rendered with its reference data and no
record, and the banner said only "Failed to load data" - which reads like a
backend or schema fault and was twice diagnosed as one. The server logs settled
it: every reference endpoint answered 200 and the record was never requested.

MachineForm already carried a comment describing this exact trap, added when
pcsRes hit it. Two adjacent lines had the same defect and were missed, so the
comment now sits above all of them.

Report the failure honestly while here. apiError only reads err.response, so a
client-side TypeError produced nothing but the fallback string no matter how
many times the page was reloaded. Fall back to err.message when there is no
response, which is what identified this.
This commit is contained in:
benjamin.baker
2026-09-05 04:39:11 -04:00
parent 2a8dcc6db9
commit 539af3073f
3 changed files with 17 additions and 8 deletions

View File

@@ -573,12 +573,14 @@ onMounted(async () => {
operatingsystemsApi.list({ perpage: 100 }),
computersApi.protocols.list(),
businessunitsApi.listAll(),
// Handles its own failure: a site without printers still gets a form.
])
pcTypes.value = ptRes.data.data || []
statuses.value = statusRes.data.data || []
vendors.value = vendorRes.data.data || []
// listAll() pages past the server's 100-row cap and returns the ROWS, not
// an axios response, so these are read directly. Reading .data.data here
// throws and takes the whole form down with it.
vendors.value = vendorRes || []
models.value = allModels
locations.value = locRes || []
operatingsystems.value = osRes.data.data || []
@@ -636,7 +638,11 @@ onMounted(async () => {
}
} catch (err) {
console.error('Error loading data:', err)
error.value = 'Failed to load data'
// A client-side TypeError has no err.response, so apiError() would report
// only the fallback and hide which field broke. Name it either way.
error.value = err?.response
? apiError(err, 'Failed to load data')
: `Failed to load data: ${err?.message || err}`
} finally {
loading.value = false
}

View File

@@ -591,14 +591,14 @@ onMounted(async () => {
machineTypes.value = typesRes.data.data || []
statuses.value = statusRes.data.data || []
vendors.value = vendorRes.data.data || []
locations.value = locRes || []
models.value = allModels
businessunits.value = buRes.data.data || []
// listAll resolves to the ARRAY, not a response: fetchAllPages already
// unwrapped every page. Reading .data.data off it threw, and the whole
// parallel load went to the catch - so every dropdown on this form came up
// empty and the machine's own values never loaded.
vendors.value = vendorRes || []
locations.value = locRes || []
models.value = allModels
businessunits.value = buRes || []
pcs.value = pcsRes || []
// Load relationship types separately

View File

@@ -187,8 +187,11 @@ onMounted(async () => {
])
types.value = typesResponse.data.data || []
statuses.value = statusResponse.data.data || []
// listAll resolves to the ARRAY, not a response: fetchAllPages already
// unwrapped every page. Reading .data.data off it throws and takes the
// whole parallel load into the catch.
locations.value = locResponse || []
businessunits.value = buResponse.data.data || []
businessunits.value = buResponse || []
const assetType = (assetTypesResponse.data.data || []).find(a => a.assettype === 'measuring_tool')
assettypeid.value = assetType ? assetType.assettypeid : null