jest-native
jest-native copied to clipboard
.toBeDisabled() buggy with RN 0.62
react-nativeorexpo: 0.62.1@testing-library/react-nativeversion: 3.1.0react-nativeversion: 0.62.1nodeversion: 12.16.1
Latest version of RN deprecated accessibilityStates in favor of accessibilityState
https://reactnative.dev/blog/2020/03/26/version-0.62#breaking-changes
Seems like now it's an object https://github.com/facebook/react-native/commit/7b35f427fd66cb0f36921b992095fe5b3c14d8b9
I suspect we need to change it here https://github.com/testing-library/jest-native/blob/77ca4408081e3371aeffe739ad12928c9119ff95/src/to-be-disabled.js#L28
It's quite weird that in my codebase everything works fine except 1 use case where I have something like this
<TouchableOpacity disabled testID="button">
<Button disabled>
And when I check it fails, no matter if the received output from jest seems to be correct and it has the disabled prop and it's true
{
"disabled": true,
"testID": "button",
"children": <Button>
}
Can you help us fix this issue by submitting a pull request?
I checked the codebase and there is an intense use of ramda which hurts my eyes and find it quite difficult to work with, but I'll try to make a PR 😄
I think I've found the issue
<TouchableOpacity testID="buttonSendLink" disabled={true}
Then checking
function isElementDisabled(element) {
const propDisabled = path(['props', 'disabled'], element);
// propDisabled = true
const stateDisabled = compose(
includes('disabled'),
defaultTo([]),
path(['props', 'accessibilityStates']),
)(element);
// stateDisabled = false (this has to change btw)
return Boolean(DISABLE_TYPES.includes(getType(element)) && (propDisabled || stateDisabled));
}
The issue is with DISABLE_TYPES.includes(getType(element)
Because getType(element) returns
{ '$$typeof': Symbol(react.forward_ref), render: [Function] }
Something might have changed in the TouchableOpacity export in React Native and now that's what happens
Yes seems to be related https://github.com/facebook/react-native/issues/27721
Is there any update on this? Or a good workaround? I seem to be experiencing the same problem with the Pressable component on 0.63.2.
About the new prop accessibilityState in favor of AccessibilityStates I have an open PR #30. I didn't have the chance to look at this, though.
Seems like the only workaround for this one is mocking TouchableOpacity, TouchableHighlight, and Pressable.
Something like this: jest.mock('react-native/Libraries/Components/Touchable/TouchableOpacity', () => 'TouchableOpacity');
Do you guys think it would be a good solution to doing this mock on our side :thinking: ? @thymikee thoughts?
I'd like to avoid custom mocks other than the one provided by the core. Does it work with @testing-library/[email protected]? It's a prerelease sourced from react-native-testing-library. Here's the migration guide: https://github.com/callstack/react-native-testing-library/blob/7.x/website/docs/MigrationV7.md#guide-for-testing-libraryreact-native-users
It probably shouldn't work. The issue here is that RN exported TouchableHighlight and TouchableOpacity with React.forwardRef without a displayName.
https://github.com/facebook/react-native/blob/master/Libraries/Components/Touchable/TouchableHighlight.js#L382 https://github.com/facebook/react-native/blob/master/Libraries/Components/Touchable/TouchableOpacity.js#L301
The matcher to-be-disabled is checking for one of those components:
const DISABLE_TYPES = [
'Button',
'Slider',
'Switch',
'Text',
'TouchableHighlight',
'TouchableOpacity',
'TouchableWithoutFeedback',
'View',
'TextInput',
];
and since forwardRef does not has a displayName, it does not match.
Looks like it's fixed on master: https://github.com/facebook/react-native/commit/4b935ae95f09e4a1eb1e5ac8089eb258222a0f8b
It turns out this commit didn't fix :disappointed: . Touchables aren't being mocked on RN setup.js So I opened a PR to fix that: https://github.com/facebook/react-native/pull/29531
@thymikee @mdjastrzebski as we discussed on #36, what do you guys think about also removing this DISABLE_TYPES from this matcher? It has the same purpose as the VALID_ELEMENTS.
@brunohkbx
We definitely should update the current code, however just removing DISABLE_TYPES will probably not be enough.
Disabled element checks in RNTL have their own logic, which is different than just checking disabled prop. It follows RN code and uses View.onStartShouldSetResponder prop. So most probably we should use the same logic here.
See: https://github.com/callstack/react-native-testing-library/pull/460
As a separate case we should think whether TextInput editable=false is a disabled element or not.
@mdjastrzebski would you mind reviewing it? #50
Closing as stale.