test: add deterministic resilience matrix

This commit is contained in:
2026-09-02 07:24:48 +03:00
parent 5abd1c19ae
commit 8089d061ec
21 changed files with 809 additions and 22 deletions

View File

@@ -1,6 +1,10 @@
<script setup lang="ts">
import { computed, nextTick, onUnmounted, ref, shallowRef, watch } from 'vue';
import { useLazyMedia } from '@/composables/useLazyMedia';
import { isTestFault, recordTestFaultEvent } from '@/testing/fault-hooks';
declare const __PORTFOLIO_TEST_BUILD__: boolean;
const TEST_BUILD = typeof __PORTFOLIO_TEST_BUILD__ !== 'undefined' && __PORTFOLIO_TEST_BUILD__;
export interface AccessibleVideoSource {
src: string;
@@ -64,6 +68,11 @@ const markUnavailable = (): void => {
const play = async (): Promise<void> => {
if (unavailable.value) return;
if (TEST_BUILD && isTestFault('F8-video-failure')) {
recordTestFaultEvent('video-failure');
markUnavailable();
return;
}
lazy.requestExplicit();
status.value = 'Loading video.';
await nextTick();

View File

@@ -39,7 +39,7 @@ const statusText = computed(() => {
if (props.policy.reason === 'data-saver') return 'Motion: static — data saver is active';
if (props.policy.reason === 'visitor-pause') return 'Motion: paused';
if (props.policy.reason === 'saved-static') return 'Motion: static';
if (props.sceneStatus === 'failed' || props.sceneStatus === 'static') return 'Motion: static — scene unavailable';
if (props.sceneStatus === 'failed' || props.sceneStatus === 'static') return 'Visuals unavailable';
if (props.sceneStatus === 'loading' || props.sceneStatus === 'idle') return 'Motion: preparing';
return 'Motion: active';
});

View File

@@ -3,6 +3,10 @@ import { computed, onMounted, ref, toRef, watch } from 'vue';
import { useSceneController, type SceneHostState } from '@/composables/useSceneController';
import type { JourneySnapshot } from '@/journey/types';
import type { MotionPolicy, QualityTier } from '@/journey/motion-policy';
import { isTestFault, recordTestFaultEvent } from '@/testing/fault-hooks';
declare const __PORTFOLIO_TEST_BUILD__: boolean;
const TEST_BUILD = typeof __PORTFOLIO_TEST_BUILD__ !== 'undefined' && __PORTFOLIO_TEST_BUILD__;
const props = defineProps<{
journey: JourneySnapshot;
@@ -18,6 +22,7 @@ const emit = defineEmits<{
const canvas = ref<HTMLCanvasElement | null>(null);
const clientReady = ref(false);
const posterFailed = ref(TEST_BUILD && isTestFault('F7-poster-failure'));
const journey = toRef(props, 'journey');
const policy = toRef(props, 'policy');
const quality = toRef(props, 'quality');
@@ -35,6 +40,7 @@ const showCanvas = computed(() => (
watch(scene.state, (state) => emit('stateChange', state), { immediate: true });
onMounted(() => { clientReady.value = true; });
if (posterFailed.value) recordTestFaultEvent('poster-failure');
</script>
<template>
@@ -44,8 +50,10 @@ onMounted(() => { clientReady.value = true; });
aria-hidden="true"
:data-scene-state="sceneState"
:data-scene-generation="sceneGeneration"
:data-static-fallback="!showCanvas"
:data-poster-failed="posterFailed"
>
<img class="journey-poster" alt="" width="1600" height="900">
<img v-if="!posterFailed" class="journey-poster" alt="" width="1600" height="900" @error="posterFailed = true">
<canvas v-if="showCanvas" ref="canvas" class="journey-canvas" aria-hidden="true" />
</div>
<slot />