简体   繁体   中英

Dispatching an imported function in React Native Redux

This is my first time using React Native and only briefly worked with Redux but I have a function in my Redux/authentication.js that is supposed to create a new account with Firebase.

export function handleAuthWithFirebase (newUser) {
    return function (dispatch, getState) {
        dispatch(authenticating());

        console.log(newUser);
        console.log('Signing up user');
        var email = newUser.email;
        var password = newUser.password;

        firebase.auth().createUserWithEmailAndPassword(email, password).catch(error => {
        // Handle Errors here.
        var errorCode = error.code;
        var errorMessage = error.message;
        // ...
        }).then(() => {

            var user = firebaseAuth.currentUser;
            // Set user in Firebase
            firebase.database().ref('/users/' + user.uid).set({
                displayName: newUser.displayName,
                userName: newUser.userName,
                email: newUser.email
            })
        })

        dispatch(isAuthed(user.uid))
    }
}

I import this function into a SignUpForm component that gets user information for a few <TextInput/> 's. So now I want to run the handleSignUp function but I'm not entirely sure how.

class SignUpForm extends Component {
    static propTypes = {

    }
    state = {
        email: '',
        password: '',
        username: '',
        displayName: ''
    }
    handleSignUp () {

        // Want to call handleAuthWithFirebase(this.state) here.    

    }
    render () {
        console.log(this.props);
        return (
            <View style={{flex: 1}}>
                <View>
                    <TextInput
                        style={styles.input}
                        onChangeText={(email) => this.setState({email})} 
                        value={this.state.email} 
                        autoCorrect={false}
                    />
                    <TextInput 
                        style={styles.input}
                        onChangeText={(password) => this.setState({password})}
                        value={this.state.password} 
                        autoCorrect={false}
                    />
                    <TextInput 
                        style={styles.input}
                        onChangeText={(username) => this.setState({username})}
                        value={this.state.username} 
                        autoCorrect={false}
                    />
                    <TextInput 
                        style={styles.input}
                        onChangeText={(displayName) => this.setState({displayName})}
                        value={this.state.displayName} 
                        autoCorrect={false}
                    />
                </View>
                <View>
                    <Button title="Sign Up" onPress={this.handleSignUp}>Sign Up</Button>
                </View>
            </View>
        )
    }
}

export default connect()(SignUpForm)

It's showing me that dispatch is available as a prop when I console.log(this.props)

在此处输入图片说明

but when I try and do this.props.dispatch(handleAuthWithFirebase(this.state)) in the handleSignUp method I get an error that props is undefined

That is because your callback has a scope of its own, as it is a named function. Just bind it in your button like this:

<Button title="Sign Up" onPress={this.handleSignUp.bind(this)}>Sign Up</Button>

The reason for this is that the scope of the function changes when invoked from a different context, unless you explicitly bind the function to a certain this . You need that in order to access the props. Other than that your code looks fine, but let me know if you run into any trouble when you fix that.

When you connect your component to your store dispatch would be passed as props to your component.

In your handleSignUp you can do following:-

  handleSignUp () {
     const {dispatch} = this.props
     //input validations
     const newUser = this.state
     dispatch(handleAuthWithFirebase(newUser)) 

  }

Also for your button you need to bind this . This you can do in button

<Button title="Sign Up" onPress={this.handleSignUp.bind(this)}>Sign Up</Button>

or in the constructor

constructor(){
   super()
   this.this.handleSignUp = this.handleSignUp.bind(this)
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM