fix(frontend): re-sync the sniffing island when its value changes externally

The sniffing config editor froze its seed value at mount and only watched
its own inner AntD form, never reflecting a later change to the shared RHF
`sniffing` path. Because the inbound form mounts every tab with
forceRender, the friendly Sniffing tab and the Advanced JSON editor are live
at once: editing sniffing in the JSON editor updated the RHF value but not
the frozen island, so the next interaction with the friendly tab emitted the
stale value and silently discarded the JSON edit.

Add an effect that pushes an external value change into the inner form,
guarded by the same lastEmitted marker the emit path uses so the island
never re-seeds from its own echo and no update loop forms.
This commit is contained in:
MHSanaei
2026-07-15 06:01:33 +02:00
parent 5f7c2424ef
commit 48b60fec54
2 changed files with 29 additions and 0 deletions
@@ -27,6 +27,14 @@ export default function SniffingField({ value, onChange, enableLabel }: Sniffing
onChangeRef.current?.(sniffing);
}, [sniffing]);
useEffect(() => {
if (value === undefined) return;
const serialized = JSON.stringify(value);
if (serialized === lastEmitted.current) return;
lastEmitted.current = serialized;
form.setFieldsValue({ sniffing: value });
}, [value, form]);
return (
<Form
form={form}
@@ -0,0 +1,21 @@
import { describe, it, expect, vi } from 'vitest';
import { render } from '@testing-library/react';
import SniffingField from '@/lib/xray/forms/fields/SniffingField';
import { SniffingSchema } from '@/schemas/primitives/sniffing';
describe('SniffingField external re-sync', () => {
it('reflects an external value change (e.g. an advanced JSON edit) in the friendly form', () => {
const disabled = SniffingSchema.parse({ enabled: false });
const enabled = SniffingSchema.parse({ enabled: true });
const onChange = vi.fn();
const { rerender, getByRole } = render(
<SniffingField value={disabled} onChange={onChange} enableLabel="Enable" />,
);
expect(getByRole('switch').getAttribute('aria-checked')).toBe('false');
rerender(<SniffingField value={enabled} onChange={onChange} enableLabel="Enable" />);
expect(getByRole('switch').getAttribute('aria-checked')).toBe('true');
});
});