I am trying to make an app where the USER_ID
is loaded from the device’s local storage if found, otherwise, a new id is generated and stored in the local storage. I am trying to make use of React useContext()
to make the USER_ID
visible to the whole app after it is first run.
import React, {useEffect, useState} from 'react';
import AsyncStorage from '@react-native-async-storage/async-storage';
import uuid from 'react-native-uuid';
export const UserIdContext = React.createContext('undef');
export const UserIdProvider = ({children}) => {
const [userId, setUserId] = useState('');
useEffect(() => {
async function getOrInitUserId() {
try {
let temp = await AsyncStorage.getItem('USER_ID');
if (temp == null) {
temp = uuid.v4();
await AsyncStorage.setItem('USER_ID', uuid.v4());
console.log('USER_ID Generated: ' + temp);
} else {
console.log('USER_ID Found: ' + temp);
}
setUserId(temp);
} catch (error) {
console.error(error);
}
}
if (!userId) {
getOrInitUserId();
}
});
return (
<UserIdContext.Provider value={userId}>{children}</UserIdContext.Provider>
);
};
export const useUserId = () => React.useContext(UserIdContext);
The provider is used as below:
const App = () => {
useEffect(() => {
....
});
return (
<UserIdProvider>
...contents of app...
</UserIdProvider>
);
};
export default App;
However, the useEffect()
of < UserIdProvider />
is not run as the app is launched for the first time after being installed on a device, as there is no log on the console. After the app is closed/quit and relaunched, the console log a USER_ID
found, instead of USER_ID
generated.
2
Answers
Add 2nd argument as [] so it will render only once. Otherwise, it will render every time when any state will be updated.
In order to trigger
useEffect
when first run you should enter[]
as prop like this: