Skip to content

Commit

Permalink
Refactor around missing dependency in Link Control internal value syn…
Browse files Browse the repository at this point in the history
…c effect (#49509)

* Remove syncing

* Add test coverage

* Reinstate state “reset” but avoid passing internalInputValue as dep to effect

* Update packages/block-editor/src/components/link-control/test/index.js

---------

Co-authored-by: Ben Dwyer <ben@scruffian.com>
  • Loading branch information
getdave and scruffian authored May 4, 2023
1 parent 893d620 commit 4a76c7a
Show file tree
Hide file tree
Showing 2 changed files with 50 additions and 7 deletions.
42 changes: 42 additions & 0 deletions packages/block-editor/src/components/link-control/test/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2235,6 +2235,48 @@ describe( 'Controlling link title text', () => {
screen.queryByRole( 'textbox', { name: 'Text' } )
).not.toBeInTheDocument();
} );

it( 'should reset state on value change', async () => {
const user = userEvent.setup();
const textValue = 'My new text value';
const mockOnChange = jest.fn();

const { rerender } = render(
<LinkControl
value={ selectedLink }
forceIsEditingLink
hasTextControl
onChange={ mockOnChange }
/>
);

await toggleSettingsDrawer( user );

const textInput = screen.queryByRole( 'textbox', { name: 'Text' } );

expect( textInput ).toBeVisible();

await user.clear( textInput );
await user.keyboard( textValue );

// Was originally title: 'Hello Page', but we've changed it.
rerender(
<LinkControl
value={ {
...selectedLink,
title: 'Something else',
} }
forceIsEditingLink
hasTextControl
onChange={ mockOnChange }
/>
);

// The text input should not be showing as the form is submitted.
expect( screen.queryByRole( 'textbox', { name: 'Text' } ) ).toHaveValue(
'Something else'
);
} );
} );

async function toggleSettingsDrawer( user ) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,15 @@ export default function useInternalInputValue( value ) {
value || ''
);

// If the value prop changes, update the internal state.
useEffect( () => {
/**
* If the value changes then sync this
* back up with state.
*/
if ( value && value !== internalInputValue ) {
setInternalInputValue( value );
}
setInternalInputValue( ( prevValue ) => {
if ( value && value !== prevValue ) {
return value;
}

return prevValue;
} );
}, [ value ] );

return [ internalInputValue, setInternalInputValue ];
Expand Down

0 comments on commit 4a76c7a

Please sign in to comment.