diff --git a/tests/wallets/index.html b/tests/wallets/index.html index fc727f9cf..8a83c6d0c 100644 --- a/tests/wallets/index.html +++ b/tests/wallets/index.html @@ -199,6 +199,10 @@ height: 100%; } + .picker-card--full { + grid-column: 1 / -1; + } + .picker-card .q-card__section--vert { height: 100%; padding: 16px 18px; @@ -590,6 +594,20 @@ background: rgba(25, 54, 61, 0.03); } + .test-mock-item-grid { + display: grid; + gap: 12px; + grid-template-columns: repeat(2, minmax(0, 1fr)); + } + + .test-mock-item-json { + min-height: 160px; + } + + .test-mock-item-full { + grid-column: 1 / -1; + } + .detail-label { color: var(--studio-muted); font-size: 0.74rem; @@ -888,18 +906,78 @@ gap: 12px; } + .function-tabs { + margin-bottom: 14px; + border-radius: 18px; + background: rgba(22, 32, 40, 0.04); + padding: 6px; + } + + .function-tabs .q-tab { + flex: 1 1 0; + min-width: 0; + justify-content: center; + min-height: 48px; + border-radius: 12px; + color: var(--q-primary); + text-align: center; + } + + .function-tabs .q-tab__content { + align-items: center; + justify-content: center; + width: 100%; + } + + .function-tabs .q-tab--active { + background: var(--q-primary); + color: white; + } + + .function-tabs .q-tab--active, + .function-tabs .q-tab--active .q-tab__label, + .function-tabs .q-tab--active .text-weight-bold, + .function-tabs .q-tab--active .text-caption { + color: white !important; + } + + .function-content { + min-width: 0; + } + + .function-content-header { + display: flex; + gap: 12px; + align-items: flex-start; + justify-content: space-between; + margin-bottom: 12px; + } + + .test-type-layout { + display: grid; + gap: 18px; + grid-template-columns: minmax(220px, 260px) minmax(0, 1fr); + align-items: start; + } + .test-type-tabs { - margin-top: 8px; border-radius: 18px; background: rgba(22, 32, 40, 0.04); padding: 6px; } .test-type-tabs .q-tab { - flex: 1 1 0; - min-width: 0; + justify-content: flex-start; + min-height: 48px; border-radius: 12px; color: var(--q-primary); + text-align: left; + } + + .test-type-tabs .q-tab__content { + align-items: flex-start; + justify-content: center; + width: 100%; } .test-type-tabs .q-tab--active { @@ -914,9 +992,9 @@ } .test-type-panels { - margin-top: 14px; background: transparent; box-shadow: none; + min-width: 0; } .test-type-panel { @@ -1110,8 +1188,13 @@ grid-template-columns: 1fr; } + .test-type-layout { + grid-template-columns: 1fr; + } + .mock-source-grid, .test-detail-grid, + .test-mock-item-grid, .settings-row-grid, .settings-table-grid { grid-template-columns: 1fr; @@ -1226,7 +1309,7 @@
- +
@@ -1280,327 +1363,401 @@ - - -
-
-

Function

-
- Choose the wallet interface method to inspect for the selected funding source. -
-
-
- - -
- - - - - -
-
-
-
- + -
-
-

Tests For Selected Function

-
- Browse the raw test types for this function, then inspect the call params, expected result, and selected funding source mocks. -
-
-
- -
{{ group.label }}
+
+
{{ fn.name }}
+
{{ fn.tests.length }} tests
+
- - -
-
+
+
+ +
+ +
+ -
-
-

- {{ - `${group.label} ${entryIndex + 1}` - }} -

-
- Raw test {{ testEntry.index + 1 }} -
-
+ +
{{ group.label }}
+
+ -
- - {{ testEntry.status.label }} - - - {{ currentFundingSource.name }} - - - {{ testEntry.variantCount }} generated variants - -
-
- -
- {{ testEntry.note }} -
- -
-
- - -
- {{ testEntry.callParamsError }} -
-
-
- - -
- {{ testEntry.expectedError }} -
-
-
- -
-
-
-
-
{{ mockSet.label }}
+ + +
+
+
+
+

+ {{ + `${group.label} ${entryIndex + 1}` + }} +

+
+ Raw test {{ testEntry.index + 1 }}
+
+ +
+ + {{ testEntry.status.label }} + + + {{ currentFundingSource.name }} + - {{ mockSet.bindings.length }} function mocks + {{ testEntry.variantCount }} generated variants
+
-
+
+ {{ testEntry.note }} +
+ +
+
- + @blur="persistTestCallParams(testEntry)" + > +
+ {{ testEntry.callParamsError }} +
+
+ + +
+ {{ testEntry.expectedError }} +
+
+
+
-
-
- - - - +
+
+
{{ mockSet.label }}
+ + {{ mockSet.bindings.length }} function mocks +
-
-
+
+ Description + +
-
- No objects are defined in this mock array yet. +
+
+
+ + + + +
+
+ +
+
+
+
+

{{ testMockItemTitle(item, itemIndex) }}

+
+ +
+ +
+ +
+ +
+
+ + +
+ +
+ + +
+ +
+ + +
+ {{ item.requestBodyError }} +
+
+ +
+ + +
+ +
+ + +
+ {{ item.responseError }} +
+
+
+ +
+ {{ item.error }} +
+
+
+ +
+ No objects are defined in this mock array yet. +
+ +
+ +
-
-
- -
- -
- {{ mockSet.error }} +
+ {{ mockSet.error }} +
-
-
- No wallet-specific mock entry is defined for - {{ currentFundingSource.name }} - in this test. +
+ No wallet-specific mock entry is defined for + {{ currentFundingSource.name }} + in this test. +
+ +
- - -
- No tests are defined for this function. +
+ No tests are defined for this function. +
+
+
+ +
+ No functions are defined for this fixture file.
@@ -2473,6 +2630,30 @@ } } + function createTestMockItemDraftState(item = {}) { + const source = isPlainObject(item) ? item : {} + + return { + descriptionText: + typeof source.description === 'string' ? source.description : '', + skip: typeof source.skip === 'boolean' ? source.skip : false, + hasSkipField: typeof source.skip === 'boolean', + requestType: + typeof source.request_type === 'string' ? source.request_type : '', + requestBodyText: + source.request_body !== undefined + ? safeStringify(source.request_body) + : '', + requestBodyError: '', + responseType: + typeof source.response_type === 'string' ? source.response_type : '', + responseText: + source.response !== undefined ? safeStringify(source.response) : '', + responseError: '', + error: '' + } + } + function inferDatasetKeyFromData(data) { let rpcHint = false @@ -2757,11 +2938,8 @@ .filter(([key]) => key !== 'description') .map(([key, value]) => ({ selectedMockName: key, - itemTexts: (Array.isArray(value) ? value : [value]).map( - item => ({ - text: safeStringify(item), - error: '' - }) + items: (Array.isArray(value) ? value : [value]).map(item => + createTestMockItemDraftState(item) ) })), error: '' @@ -3003,10 +3181,7 @@ return { selectedMockName: mockName, - itemTexts: normalizedItems.map(item => ({ - text: safeStringify(item), - error: '' - })) + items: normalizedItems.map(item => createTestMockItemDraftState(item)) } }, testMockBindingOptions(selectedMockName = '') { @@ -3037,8 +3212,7 @@ return availableName?.value || '' }, testMockItemTitle(item, itemIndex) { - const parsed = parseJsonText(item?.text || '') - const description = parsed.ok ? parsed.data?.description : '' + const description = item?.descriptionText || '' if (typeof description === 'string' && description.trim() !== '') { return description.trim() @@ -3047,48 +3221,15 @@ return `Test Mock Definition ${itemIndex + 1}` }, testMockItemHasSkip(item) { - const parsed = parseJsonText(item?.text || '') - - return ( - parsed.ok && - isPlainObject(parsed.data) && - typeof parsed.data.skip === 'boolean' - ) + return Boolean(item?.hasSkipField || item?.skip === true) }, testMockItemSkip(item) { - const parsed = parseJsonText(item?.text || '') - - if ( - !parsed.ok || - !isPlainObject(parsed.data) || - typeof parsed.data.skip !== 'boolean' - ) { - return false - } - - return parsed.data.skip + return Boolean(item?.skip) }, setTestMockItemSkip(testEntry, mockSet, item, value) { - const parsed = parseJsonText(item?.text || '') - - if ( - !parsed.ok || - !isPlainObject(parsed.data) || - typeof parsed.data.skip !== 'boolean' - ) { - item.error = - 'Could not update skip because this mock definition is not valid JSON with a boolean skip field.' - this.notify( - 'Could not save mock skip flag.', - 'negative', - item.error - ) - return - } - item.error = '' - parsed.data.skip = Boolean(value) - item.text = safeStringify(parsed.data) + item.hasSkipField = true + item.skip = Boolean(value) this.persistTestMockSet(testEntry, mockSet) }, addTestMockBinding(testEntry, mockSet) { @@ -3101,14 +3242,11 @@ this.persistTestMockSet(testEntry, mockSet) }, addTestMockBindingItem(testEntry, mockSet, binding) { - binding.itemTexts.push({ - text: safeStringify({}), - error: '' - }) + binding.items.push(createTestMockItemDraftState({})) this.persistTestMockSet(testEntry, mockSet) }, removeTestMockBindingItem(testEntry, mockSet, binding, itemIndex) { - binding.itemTexts.splice(itemIndex, 1) + binding.items.splice(itemIndex, 1) this.persistTestMockSet(testEntry, mockSet) }, getSettingsDraftRows(datasetKey, fundingSourceName) { @@ -3374,8 +3512,10 @@ mockSet.error = '' ;(mockSet.bindings || []).forEach(binding => { - ;(binding.itemTexts || []).forEach(item => { + ;(binding.items || []).forEach(item => { item.error = '' + item.requestBodyError = '' + item.responseError = '' }) }) @@ -3385,7 +3525,7 @@ const mockName = (binding.selectedMockName || '').trim() if (!mockName) { - if ((binding.itemTexts || []).length) { + if ((binding.items || []).length) { mockSet.error = 'Select a function mock before editing its overrides.' this.notify( 'Could not save test mock definition.', @@ -3410,27 +3550,65 @@ const parsedItems = [] - for (let itemIndex = 0; itemIndex < (binding.itemTexts || []).length; itemIndex += 1) { - const item = binding.itemTexts[itemIndex] + for (let itemIndex = 0; itemIndex < (binding.items || []).length; itemIndex += 1) { + const item = binding.items[itemIndex] + const nextItem = {} - try { - parsedItems.push( - this.parseEditableTestJson( - item.text, - `${mockName} item ${itemIndex + 1}` - ) - ) - } catch (error) { - item.error = - error instanceof Error ? error.message : String(error) - mockSet.error = item.error - this.notify( - 'Could not save test mock definition.', - 'negative', - mockSet.error - ) - return + if ((item.descriptionText || '').trim() !== '') { + nextItem.description = item.descriptionText.trim() } + + if (item.hasSkipField || item.skip === true) { + nextItem.skip = Boolean(item.skip) + } + + if ((item.requestType || '').trim() !== '') { + nextItem.request_type = item.requestType.trim() + } + + if ((item.requestBodyText || '').trim() !== '') { + try { + nextItem.request_body = this.parseEditableTestJson( + item.requestBodyText, + `${mockName} request_body ${itemIndex + 1}` + ) + } catch (error) { + item.requestBodyError = + error instanceof Error ? error.message : String(error) + mockSet.error = item.requestBodyError + this.notify( + 'Could not save test mock definition.', + 'negative', + mockSet.error + ) + return + } + } + + if ((item.responseType || '').trim() !== '') { + nextItem.response_type = item.responseType.trim() + } + + if ((item.responseText || '').trim() !== '') { + try { + nextItem.response = this.parseEditableTestJson( + item.responseText, + `${mockName} response ${itemIndex + 1}` + ) + } catch (error) { + item.responseError = + error instanceof Error ? error.message : String(error) + mockSet.error = item.responseError + this.notify( + 'Could not save test mock definition.', + 'negative', + mockSet.error + ) + return + } + } + + parsedItems.push(nextItem) } nextValue[mockName] = parsedItems