i want to use query inside child object of Category but im gettin this error.
Unhandled Runtime Error Error:
QueryClientProvider to set one No QueryClient set, use QueryClientProvider to set one
pages/category/[pid].js
15 | heading: pid,
16 | };
> 17 | const { data, isLoading } = useQuery(["movieImage"], get);
| ^
18 | if (isLoading) {
19 | return <div>Loading...</div>;
20 | }
index.js
import Banner from '../components/Banner';
import Category from '../components/Category';
import LiveAuction from '../components/LiveAuction';
import TopCollectors from '../components/TopCollectors';
import TrendingNow from '../components/TrendingNow';
import { ReactQueryDevtools } from "react-query/devtools";
import {
QueryClient,
QueryClientProvider,
} from "react-query";
import { Fragment } from 'react';
const queryClient = new QueryClient();
const Home = () => {
return (
<Fragment>
{" "}
<QueryClientProvider client={queryClient} contextSharing={true}>
<Banner />
<Category />
<LiveAuction />
<TopCollectors />
<TrendingNow />
<ReactQueryDevtools initialIsOpen={true} />
</QueryClientProvider>
</Fragment>
);
}
export default Home
some part of pages/category/[pid].js
const { pid } = router.query;
const { data, isLoading } = useQuery(["movieImage"], getGenres);
if (isLoading) {
return <div>Loading...</div>;
}
tried to change ReactQueryDevtools position
added Fragment
added contextSharing={true} to QueryClientProvider
Related
I'm trying to test component that is wrapped with other component, the parent component has conditional rendering, for explanation:
import React, { FunctionComponent } from 'react'
import { getPermissions, ROLES, PERMISSIONS } from '~/constants/permissions'
import usePermission from '~/hooks/usePermission'
export interface UsePermissionParams {
as: ROLES;
children?: React.ReactNode;
permissions: PERMISSIONS[];
}
// This Component is used to check if the user has the permission to access Specific Component or part of the UI
const CanAccess: FunctionComponent<UsePermissionParams> = ({
as,
children,
permissions,
}) => {
const hasPermission = usePermission({ permissions })
if (as === ROLES.VENDOR) {
const hasAllPermissions = permissions?.every((permission) =>
getPermissions.vendor.includes(permission)
)
if (hasPermission && hasAllPermissions) {
return <>{children}</>
}
} else if (as === ROLES.ADMIN) {
const hasAllPermissions = permissions?.every((permission) =>
getPermissions.admin.includes(permission)
)
if (hasPermission && hasAllPermissions) {
return <>{children}</>
}
}
return <></>
}
export default CanAccess
this is the parent component that wrap the component that I need to test.
and this is the component that I want to test:
import React, { useContext, useState } from 'react'
import { CircularProgress } from '#mui/material'
import { useSelector } from 'react-redux'
import CanAccess from '~/components/CanAccess'
import CreateBox from '~/components/CreateBox'
import { ROLES, PERMISSIONS } from '~/constants/permissions'
import CardHolder from '~/modules/finance/Components/SponsoredProductsTab/Components/CardHolder'
import TopUpModal from '~/modules/finance/Components/TopUpModal'
import { FinanceContext } from '~/modules/finance/FinanceContext'
import * as styles from '~/modules/finance/styles'
import { State } from '~/store'
import { User } from '~/store/user/types'
import { i18n } from '~/translations/i18n'
import { currencySign } from '~/utils/getCurrencySign'
import { ls } from '~/utils/localStorage'
import { separator } from '~/utils/numberSeperator'
const AccountBalance = () => {
const { list, loading } = useContext<any>(FinanceContext)
const [showTopUpModal, setShowTopUpModal] = useState<boolean>(false)
const userRepresentation = useSelector<State, User | null>(
(state) => state.user.data
)
const targetSelected = ls.get('target_code')
const handleOpenTopUpModal = () => {
setShowTopUpModal(true)
}
const onClose = () => {
setShowTopUpModal(false)
}
const renderCreateTopUP = () => (
<CanAccess as={ROLES.VENDOR} permissions={[PERMISSIONS.FO_TOPUP_ACCESS]}>
<CreateBox
label="Top Up"
maxWidth="fit-content"
handleCreateCampaign={handleOpenTopUpModal}
/>
</CanAccess>
)
return (
<>
{showTopUpModal && (
<TopUpModal
onClose={onClose}
advertiserId={
userRepresentation == null
? 0
: userRepresentation?.advertiserId || 0
}
target={targetSelected}
open
/>
)}
<CardHolder
cardHeader="Your account balance:"
cardContent={`${currencySign() || ''} ${
separator(list?.balance) || '0'
}`}
CardBottom={renderCreateTopUP()}
/>
</>
)
}
export default AccountBalance
and this is the test file:
import AccountBalance from '.'
import { render, screen } from '~/test-utils'
describe('AccountBalance', () => {
it('should render the top up button', async () => {
render(<AccountBalance />)
const topUpBtn = await screen.findByText('Top up')
expect(topUpBtn).toBeInTheDocument()
})
})
and I have this error:
<body>
<div>
<div
class="MuiPaper-root MuiPaper-elevation MuiPaper-rounded MuiPaper-elevation1 css-s9smhs-MuiPaper-root"
>
<div>
<p
class="MuiTypography-root MuiTypography-body1 css-1tvvmmg-MuiTypography-root"
>
Your account balance:
</p>
<p
class="MuiTypography-root MuiTypography-body1 css-1hd1hip-MuiTypography-root"
>
0
</p>
<div
class="css-0"
/>
</div>
</div>
</div>
</body>
5 | it('should render the top up button', async () => {
6 | render(<AccountBalance />)
> 7 | const topUpBtn = await screen.findByText('Top up')
| ^
8 | expect(topUpBtn).toBeInTheDocument()
9 | })
10 | })
the problem is: any component that is wrapped with the component CanAccess is not rendering and I have null
so what is the problem
hi i am new to react testing and i am using react testing library and jest.please help me in writing test case for below code.
import React from 'react'
import {
Loader,
SectionTitle,
ErrorLabel,
} from 'LookingGlass/common/components'
import LookingGlassPanelResultSection from 'LookingGlass/app/components/LookingGlassResultSection'
import constants from 'LookingGlass/constants'
import getErrorMessage from 'LookingGlass/app/utils/getErrorMessage'
import styles from './_.index.module.scss'
export default function LookingGlassPanelResults(props) {
const { queryResult, isTimedOut, error, isServerDown, isLoading } = props
if (isLoading)
return (
<Loader
content={constants.Loader.loaderContent}
active
inline="centered"
size="large"
/>
)
if (isServerDown) {
return <ErrorLabel text={constants.error.message.error_404} />
}
if (isTimedOut) {
return <ErrorLabel text={constants.requestsTimeout.msg} />
}
if (error) {
return <ErrorLabel text={getErrorMessage(error)} />
}
if (!queryResult) return null
return (
<div>
<hr className={styles.seperateLine} />
<SectionTitle text={constants.QueryPanelResult.resultPanel} />
<LookingGlassPanelResultSection queryResult={queryResult} />
</div>
)
}
ErrorLabel is different component where icon is used and text is displayed. How to write test where we use component inside component ?
this is my test case:-
const renderComponent = (props) =>
render(<LookingGlassPanelResults {...props} />)
test('Verify that isServerDown parameter works', () => {
const component = renderComponent({ isServerDown: true })
const { getByText } = within(component)
expect(
getByText('Service unavailable. Please try later'),
).toBeInTheDocument()
})
Error:-`
TypeError: Expected container to be an Element, a Document or a DocumentFragment but got Object.
20 | const { getByText } = within(component)
21 | expect(
> 22 | getByText('Service unavailable. Please try later'),
| ^
23 | ).toBeInTheDocument()
24 | })`
here first we need to get ErrorLabel by test-id and then check expectations
test('Verify that isServerDown parameter works', () => {
const component = renderComponent({ isServerDown: true })
const { getByTestId } = component
expect(getByTestId('ErrorLabel')).toHaveTextContent(
'Service unavailable. Please try later',
)
})
I am new to coding and I was wondering if someone can show me how to convert this code that was shared on Sandbox from 'React TypeScript ' to 'React js'.
import * as React from "react";
import { render } from "react-dom";
import {TreeView, TreeItem, TreeItemProps, TreeViewProps} from "#material-ui/lab"
import ExpandMoreIcon from "#material-ui/icons/ExpandMore";
import ChevronRightIcon from "#material-ui/icons/ChevronRight";
function TreeItemX(props:TreeItemProps &{iconClickOnly:boolean}){
// todo should call the original
const handler:TreeItemProps['onLabelClick'] = evt => evt.preventDefault();
const {iconClickOnly,...others} = props;
const handledProps:TreeItemProps ={
...others,
[props.iconClickOnly?'onLabelClick':'onIconClick']:handler
}
return <TreeItem {...handledProps} />
}
function TreeViewX(props:TreeViewProps&{defaultPreventedPrevents:boolean}){
const {defaultPreventedPrevents,...others} = props;
const originalOnNodeSelect = props.onNodeSelect;
const preventingOnNodeSelect = (evt:React.ChangeEvent<{}>, nodeId:string&string[]) => {
if(defaultPreventedPrevents){
if(!evt.defaultPrevented){
originalOnNodeSelect?.(evt,nodeId)
}
}else{
if(evt.defaultPrevented){
originalOnNodeSelect?.(evt,nodeId)
}
}
}
return <TreeView {...others} onNodeSelect={preventingOnNodeSelect}/>
}
function App(){
const [selected,setSelected] = React.useState<string>('')
return (
<TreeViewX
defaultPreventedPrevents={true}
defaultCollapseIcon={<ExpandMoreIcon />}
defaultExpandIcon={<ChevronRightIcon />}
selected={selected}
onNodeSelect={(_,id)=>{
setSelected(id);
}}>
<TreeItemX iconClickOnly nodeId='parent' label='Parent'>
<TreeItemX iconClickOnly nodeId='child' label='Child'/>
</TreeItemX>
</TreeViewX>
);
}
render(<App />, document.getElementById("root"));
Thank you in advance.
A good start would be to remove the types, for example:
function TreeItemX(props){
const handler = evt => evt.preventDefault();
const { iconClickOnly, ...others } = props;
const handledProps ={
...others,
[props.iconClickOnly ? 'onLabelClick' : 'onIconClick']
}
return <TreeItem {...handledProps} />
}
Just continue doing this, until you have your React code without the types in it.
Thank you so much for your assistance. I get the following error when I attempt to compile:
./src/App.js Line 17:3: Parsing error: Unexpected token
15 | ...others, 16 | [props.iconClickOnly ? 'onLabelClick'
: 'onIconClick']
17 | }
| ^ 18 | return 19 | } 20 |
Below is the code so far:
import React from "react";
import TreeView from "#material-ui/lab/TreeView";
import ExpandMoreIcon from "#material-ui/icons/ExpandMore";
import ChevronRightIcon from "#material-ui/icons/ChevronRight";
import TreeItem from "#material-ui/lab/TreeItem";
import "./App.css";
function TreeItemX(props){
const handler = evt => evt.preventDefault();
const { iconClickOnly, ...others } = props;
const handledProps ={
...others,
[props.iconClickOnly ? 'onLabelClick' : 'onIconClick']
}
return <TreeItem {...handledProps} />
}
function TreeViewX(props){
const {defaultPreventedPrevents,...others} = props;
const originalOnNodeSelect = props.onNodeSelect;
const preventingOnNodeSelect = (evt, nodeId) => {
if(defaultPreventedPrevents){
if(!evt.defaultPrevented){
originalOnNodeSelect?.(evt,nodeId)
}
}else{
if(evt.defaultPrevented){
originalOnNodeSelect?.(evt,nodeId)
}
}
}
return <TreeView {...others} onNodeSelect={preventingOnNodeSelect}/>
}
function App() {
return (
<div className="App">
<TreeViewX
defaultPreventedPrevents={true}
defaultCollapseIcon={<ExpandMoreIcon />}
defaultExpandIcon={<ChevronRightIcon />}
selected={selected}
onNodeSelect={(_,id)=>{
setSelected(id);
}}>
<TreeItemX iconClickOnly nodeId='parent' label='Parent'>
<TreeItemX iconClickOnly nodeId='child' label='Child'/>
</TreeItemX>
</TreeViewX>
);
</div>
);
}
export default App;
Hi i'm trying to get some data from "currency API" (https://exchangeratesapi.io/)
and this is code below
App.js
import React, { useEffect, useState, Fragment } from "react";
import Header from "./Header";
import Table from "./dashboard/Table";
import { getLatest } from "../actions/currencyAction";
import { useDispatch, useSelector } from "react-redux";
function App() {
const latest = useSelector(state => state.latest);
const dispatch = useDispatch();
useEffect(() => {
dispatch(getLatest());
}, []);
return (
<Fragment>
<Header />
{console.log(latest.rates)}
</Fragment>
);
}
export default App;
currencyAction.js
import { GET_LATEST } from "../actionType";
import axios from "axios";
export function getLatest() {
return dispatch => {
return axios.get("https://api.exchangeratesapi.io/latest").then(res => {
dispatch({ type: GET_LATEST, payload: res.data });
});
};
}
I succesfully got the data from api
<Fragment>
<Header />
{console.log(latest.rates)}
</Fragment>
{CAD: 1.4372, HKD: 8.4324, ISK: 139.3, PHP: 55.248, DKK: 7.4699, …}
CAD: 1.4372
HKD: 8.4324
ISK: 139.3
PHP: 55.248
DKK: 7.4699
HUF: 337.61
CZK: 25.186
AUD: 1.6384
RON: 4.8063
SEK: 10.5833
IDR: 15098.95
INR: 77.8265
BRL: 4.7474
RUB: 70.6675
HRK: 7.465
JPY: 120.52
THB: 34.336
CHF: 1.06
SGD: 1.5164
PLN: 4.2989
BGN: 1.9558
TRY: 6.6599
CNY: 7.6102
NOK: 10.1328
NZD: 1.7095
ZAR: 16.3592
but when I'm trying acces each currency, Everthing collapse..
<Fragment>
<Header />
{console.log(latest.rates.CAD)}
</Fragment>
TypeError: Cannot read property 'CAD' of undefined
App
C:/Users/82102/cb/src/components/App.js:17
14 |
15 | return (
16 | <Fragment>
> 17 | <Header />
| ^ 18 | {console.log(latest.rates.CAD)}
19 | </Fragment>
20 | );
I struggled for whole day long but I just can't figure out why it's happening..
please share your knowledge.. thank you
You're trying to access a property on rates before it has been loaded from the API.
The easy solution is to check its existence first:
Make sure rates is truthy (since typeof null === 'object' is also true),
Check type to see if its an object,
Then access the property.
{latest.rates && typeof latest.rates === 'object' && console.log(latest.rates.CAD)}
Because you use console.log in return causes an error.
You should do the following:
import React, { useEffect, useState, Fragment } from "react";
import Header from "./Header";
import Table from "./dashboard/Table";
import { getLatest } from "../actions/currencyAction";
import { useDispatch, useSelector } from "react-redux";
function App() {
const latest = useSelector(state => state.latest);
const dispatch = useDispatch();
useEffect(() => {
dispatch(getLatest());
}, []);
// add here
console.log(latest.rates)
return (
<Fragment>
<Header />
// remove below line
// {console.log(latest.rates)}
</Fragment>
);
}
export default App;
I am trying to write a test for a React functional component that uses Redux and Hooks.
I am using Jest with Enzyme for testing.
For Reference:
This is the functional component being tested:
import React from 'react';
import {useDispatch, useSelector} from "react-redux";
import * as actions from '../../actions/actions';
import { Button, Icon } from "#material-ui/core";
export const EditBatchHeaderComponent = (props) => {
const dispatch = useDispatch();
const { selectedBatch } = props;
const { batchName } = selectedBatch;
return (
<div className="edit-header-container">
<Button disableRipple onClick={() => {dispatch(actions.unSelectBatch())} }>
<Icon>arrow_back</Icon>
</Button>
<span>Edit Batch</span>
<span>{batchName}</span>
</div>
);
};
This is component's container:
import React from 'react';
import { BatchHeaderComponent } from './BatchHeaderComponent';
import { BatchTableComponent } from './BatchTableComponent';
import { EditBatchComponent } from './EditBatchComponent';
import {useSelector} from "react-redux";
import {EditBatchHeaderComponent} from "./EditBatchHeaderComponent";
export const BatchManagementComponent = () => {
const { selectedBatch } = useSelector(state => state.batchManagementReducer);
if (selectedBatch.length) {
return (
<div className="component-container">
<EditBatchHeaderComponent selectedBatch={selectedBatch} />
<EditBatchComponent selectedBatch={selectedBatch} />
</div>
);
}
return (
<div className="component-container">
<BatchHeaderComponent />
<BatchTableComponent />
</div>
);
};
This is the default state of the reducer:
{
sorting: {
order: '',
orderBy: ''
},
searchBy: 'batchName',
searchText: '',
filterByStatus: '--',
filterByType: '--',
waiting: false,
batchData: [],
selectedBatch: {
batchName: '',
},
}
This is the test file that is failing to recognize the props:
import React from 'react';
import { EditBatchHeaderComponent } from '../../../components/batchManagement/EditBatchHeaderComponent';
import configureStore from '../../../store';
import {Provider} from "react-redux";
import Enzyme, { mount } from "enzyme";
import Adapter from "enzyme-adapter-react-16";
import {Button} from "#material-ui/core";
Enzyme.configure({ adapter: new Adapter() });
describe('EditBatchHeaderComponent', () => {
it('mounts to the DOM successfully', () => {
const wrapper = mount(<Provider store={configureStore()}>
<EditBatchHeaderComponent />
</Provider>);
expect(wrapper.find(EditBatchHeaderComponent)).toBeDefined();
});
it('deselects the account and closes when the back button is clicked', () => {
const props = {selectedBatch: {batchName: 'INFORM'}, dispatch: jest.fn()};
const obj = {};
const wrapper = mount(
<Provider store={configureStore()}>
<EditBatchHeaderComponent {...props} />
</Provider>
);
console.log(wrapper.find(EditBatchHeaderComponent).props());
wrapper.find(Button).first().simulate('click');
expect(wrapper.find(EditBatchHeaderComponent)).toEqual(obj);
});
});
This is the error text provided by the test suite:
FAIL src/spec/components/batchManagement/EditBatchHeaderComponent.test.js (7.182s)
● EditBatchHeaderComponent › mounts to the DOM successfully
TypeError: Cannot read property 'batchName' of undefined
8 | const dispatch = useDispatch();
9 | const { selectedBatch } = props;
> 10 | const { batchName } = selectedBatch;
| ^
11 | return (
12 | <div className="edit-header-container">
13 | <Button disableRipple onClick={() => {dispatch(actions.unSelectBatch())} }>
I have run a nearly identical test on a similar component that runs and covers the code appropriately.
I can't seem to figure out why the props aren't being recognized.
Any assistance would be greatly appreciated, thanks.