I am trying to call dispatch from inside a non-component function that handles api calls. The structure is as follows:
-MainApp.js
-scripts/
--auth.js
Inside scripts/auth.js it looks like this:
export async function signIn(nav) {
const dispatch = useDispatch();
try {
...
dispatch(setIsAuthed(true));
}
...
}
I call signIn() from and onPress. I am getting an invalid hook call. What am I doing wrong?
Hooks are functions that let you “hook into” React state and lifecycle
features from function components
Don’t call Hooks from regular JavaScript functions. Instead, you can:
✅ Call Hooks from React function components.
✅ Call Hooks from custom Hooks
You should import the store and call store.dispatch to dispatch an action
The advice from Yilmaz is wrong. DO NOT DO THAT!
You should never import the store directly into the rest of the codebase. Instead, if you really must access the store elsewhere, inject it from the entry point.
Related
I want to Execute a function before loading the DOM to fetch the data from an API, I know that in vue it is with before Create but how do I do it in the VUEX store?
In VueX you execute asynchronous code in "actions". So you create an action and call it either from the beforeCreate lifecycle hook or wherever you want to put it.
To call an action you can either use this.$store.dispatch('getMatches') or you can map an action to your components method block:
methods: {
...mapActions([
'getMatches'
])
},
beforeCreate() {
this.getMatches();
}
Usually actions also start with lowercase letters, since they're methods.
In React Native, how can I perform a function when the page shows or any component shows, this really confuses me a lot, I can't find the solution in the Documents, and I use functions to declare the components.
Use a class component and and call your function in the componentDidMount lifecycle method
use can also use hook instead of componentDidMount, I personally find code more readable with hooks
import React, { useEffect } from 'react'
const Component = () => {
useEffect(() => {
//do anything here
}, [])
return(
//JSX
)
}
i'm using a global variable that is declared in a app.tsx as a functional component like
const App = () => {
useEffect(r => global.some = 'anything')
}
i'm using this global variable in other functional component very vell like this
const SomeComponent = () => {
useEffect(r => console.log(some)) //annything
}
but when i using this in a class component i gives me an error called unexpected token
like
class NewClass extends React.Component {
useEffect(r => console.log(some) //error : unexpected token
}
do someone has the answer what is going wrong what should i have to do to to log the data
useEffect belongs to react hooks and hooks only works with a functional component, not with class component.
According to docs.
Hooks are a new addition in React 16.8. They let you use state and other React features without writing a class
Link to docs
Edit: Hooks are basically a replacement of lifecycle methods in functional component, Before 16.8 we can't use lifecycle methods inside the functional component hooks made possible this for us in 16.8 version of react.
Now coming back to your question if you are doing something in functional component and wanted to do class component for the same logic you have to use lifecycle methods which since until now hooks are not available in-class component.
There is nothing that you can do with hooks and can't do with classes and vise versa.
As your comment, you have achieved the same thing with componentWillUpdate
but this method is gone a deprecate from v17 of react so if you wanted to do something while component updates you have to use componentDidUpdate is the recommended way.
here is a list that how hooks represent lifecycle methods.
https://medium.com/javascript-in-plain-english/lifecycle-methods-substitute-with-react-hooks-b173073052a
I have a React Native app where I am using HeadlessJS to call a handler on receipt of a Firebase Cloud Messaging notification.
Inside my handler which is a function, not a React component, I am accessing the Redux store using the following method:
import store from '../redux/store';
const backgroundNotificationHandler = async message => {
const state = store.getState();
...
My question is, how can I update the store in a a way that isn't a 'hack'?
Currently I have the following line in the function:
state.user.wokenFromBackgroundListener = true;
Surprisingly is works, but this is without dispatching an action or using a reducer.
Is there a better way to do it?
I can't dispatch an action because the function is not a component and it is not a component because it can't be - it requires a function as in the docs.
My code in index.js is:
AppRegistry.registerComponent(appName, () => App);
firebase.messaging().setBackgroundMessageHandler(backgroundNotificationHandler);
Dispatching from component props is just an added functionality provided by react-redux. You can still use plain redux api, in this case you can dispatch to store using store.dispatch
store.dispatch({ type: 'SOME_ACTION', payload: [1,2,3] })
However I'm not sure if you should be doing that, I haven't used HeadlessJS myself but I would first check and make sure that these task handlers are actually being run in the same context your app is running (e.g. confirm that they share store instance with your app, and NOT create a separate store just because you import store in file with the handler)
I'm creating a plugin and I just wonder why I can't access it in main.js file. Here's how Auth.js looks like:
const Auth = {
install(Vue) {
Vue.prototype.$isGuest = function () {
console.log('This user is a guest.');
}
Vue.prototype.$getAuthToken = function () {
console.log('Auth token will be returned.');
}
}
}
export default Auth
This is main.js:
import Auth from '#/helper/Auth'
Vue.use(Auth)
However, when I execute console.log(this.$isGuest()), it doesn't work. It actually returns the following:
main.js?1c90:25 Uncaught TypeError: this.$isGuest is not a function
The problem is that this method works when I call it in components such as Dashboard.vue and things like that.
I have a way to avoid calling isGuest method within main.js (I can call it in Layout.vue), but I'm more curious why it doesn't work in main.js.
Maybe because Vue hasn't been initialized yet, but even if I put the console.log() line at the end of the file, still doesn't work.
Thanks,
N.
If you are calling this.$isGuest() outside of Vue, you will get the error you describe. That's because this is not a Vue object. What this is depends on how you are building your code, but given you are using import it's probably the module.
Also, you are adding $isGuest to the prototype of Vue. That means that the function is only going to be available on actual instances of Vue objects. That is why it is available in your components.
If you want to use it in the main script, the only place you will be able to get to it is inside the Vue object in a lifecycle handler, method, or computed. For example:
new Vue({
mounted(){
console.log(this.$isGuest()) // this should work
}
})