fix(web): detail panel out of sync when reopening (#11713)

* fix(web): detail panel out of sync when reopening

* extract event handler
This commit is contained in:
Michel Heusschen 2024-08-12 14:10:43 +02:00 committed by GitHub
parent b749a68349
commit c2965c4408
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 43 additions and 17 deletions

View File

@ -1,16 +1,23 @@
import { AssetMediaResponseDto, LoginResponseDto, SharedLinkType } from '@immich/sdk';
import { expect, test } from '@playwright/test';
import type { Socket } from 'socket.io-client';
import { utils } from 'src/utils';
test.describe('Detail Panel', () => {
let admin: LoginResponseDto;
let asset: AssetMediaResponseDto;
let websocket: Socket;
test.beforeAll(async () => {
utils.initSdk();
await utils.resetDatabase();
admin = await utils.adminSetup();
asset = await utils.createAsset(admin.accessToken);
websocket = await utils.connectWebsocket(admin.accessToken);
});
test.afterAll(() => {
utils.disconnectWebsocket(websocket);
});
test('can be opened for shared links', async ({ page }) => {
@ -57,4 +64,23 @@ test.describe('Detail Panel', () => {
await expect(textarea).toBeVisible();
await expect(textarea).not.toBeDisabled();
});
test('description changes are visible after reopening', async ({ context, page }) => {
await utils.setAuthCookies(context, admin.accessToken);
await page.goto(`/photos/${asset.id}`);
await page.waitForSelector('#immich-asset-viewer');
await page.getByRole('button', { name: 'Info' }).click();
const textarea = page.getByRole('textbox', { name: 'Add a description' });
await textarea.fill('new description');
await expect(textarea).toHaveValue('new description');
await page.getByRole('button', { name: 'Info' }).click();
await expect(textarea).not.toBeVisible();
await page.getByRole('button', { name: 'Info' }).click();
await expect(textarea).toBeVisible();
await utils.waitForWebsocketEvent({ event: 'assetUpdate', id: asset.id });
await expect(textarea).toHaveValue('new description');
});
});

View File

@ -83,7 +83,7 @@
let isLiked: ActivityResponseDto | null = null;
let numberOfComments: number;
let fullscreenElement: Element;
let unsubscribe: () => void;
let unsubscribes: (() => void)[] = [];
let zoomToggle = () => void 0;
let copyImage: () => Promise<void>;
@ -172,6 +172,12 @@
}
};
const onAssetUpdate = (assetUpdate: AssetResponseDto) => {
if (assetUpdate.id === asset.id) {
asset = assetUpdate;
}
};
$: {
if (isShared && asset.id) {
handlePromiseError(getFavorite());
@ -180,11 +186,11 @@
}
onMount(async () => {
unsubscribe = websocketEvents.on('on_upload_success', (assetUpdate) => {
if (assetUpdate.id === asset.id) {
asset = assetUpdate;
}
});
unsubscribes.push(
websocketEvents.on('on_upload_success', onAssetUpdate),
websocketEvents.on('on_asset_update', onAssetUpdate),
);
await navigate({ targetRoute: 'current', assetId: asset.id });
slideshowStateUnsubscribe = slideshowState.subscribe((value) => {
if (value === SlideshowState.PlaySlideshow) {
@ -225,7 +231,10 @@
if (shuffleSlideshowUnsubscribe) {
shuffleSlideshowUnsubscribe();
}
unsubscribe?.();
for (const unsubscribe of unsubscribes) {
unsubscribe();
}
});
$: {

View File

@ -7,7 +7,6 @@
import { locale } from '$lib/stores/preferences.store';
import { featureFlags } from '$lib/stores/server-config.store';
import { user } from '$lib/stores/user.store';
import { websocketEvents } from '$lib/stores/websocket';
import { getAssetThumbnailUrl, getPeopleThumbnailUrl, handlePromiseError, isSharedLink } from '$lib/utils';
import { delay, isFlipped } from '$lib/utils/asset-utils';
import {
@ -30,7 +29,7 @@
mdiAccountOff,
} from '@mdi/js';
import { DateTime } from 'luxon';
import { createEventDispatcher, onMount } from 'svelte';
import { createEventDispatcher } from 'svelte';
import { slide } from 'svelte/transition';
import { getByteUnitString } from '$lib/utils/byte-units';
import { handleError } from '$lib/utils/handle-error';
@ -99,14 +98,6 @@
$: unassignedFaces = asset.unassignedFaces || [];
onMount(() => {
return websocketEvents.on('on_asset_update', (assetUpdate) => {
if (assetUpdate.id === asset.id) {
asset = assetUpdate;
}
});
});
const dispatch = createEventDispatcher<{
close: void;
}>();