【问题标题】:How to pass mutation variables to render function?如何将变异变量传递给渲染函数?
【发布时间】:2019-08-13 12:06:54
【问题描述】:

我有以下子组件:

class SignIn extends React.Component {

    constructor(props) {
        super(props);
        this.onClick = this.handleClick.bind(this);
        this.state = {
            email: '',
            password: ''
        };
    }

    handleClick = () => {
        this.props.onClick(this.state.email, this.state.password);            
    }

    handleEmailChange = (e) => {
        this.setState({email: e.target.value});
    }

    handlePasswordChange = (e) => {
       this.setState({password: e.target.value});
    }

    render() {
        return (
            ...
            <Input id="email" name="email" autoComplete="email" autoFocus 
                        value={this.state.email} onChange={this.handleEmailChange}/>

            <Input name="password" type="password" id="password" autoComplete="current-password" 
                        value={this.state.password} onChange={this.handlePasswordChange}/>
            ...
        );
    }
}

现在从父级我有以下组件:

class App extends Component {
    constructor(props) {
    super(props);
    this.handleClick = this.handleClick.bind(this);
    this.state = {
        email: "",
        password: ""
    }
}

handleClick(e, p, request) {
    request();
}

render() {
    const { email, password } = this.state;
    console.log('render', email, password); // here I see the right state after click
    return (
        <ApolloProvider client={client}>
            <Mutation mutation={LOGIN} variables={{ email: email, password: password }} onError={() => {}}>
            {(request, result) => {
                const { data, loading, error, called } = result;
                if(!called) {
                    return <SignIn onClick={(e, p) => this.handleClick(e, p, request)} />;
                }
                if(error) {
                    return <div>Error</div>;
                }
                if(loading) {
                    return <div>Loading...</div>;
                }
                ...
                return <div>Mutation processed</div>;
            }}
            </Mutation>
        </ApolloProvider>
    );
    }
}

我想要实现的是按钮单击后的单独处理程序,并在某些逻辑后启动突变发送。但是,这种方式变量(电子邮件、密码)总是空的发送到网络。如果我将request 直接放入句柄,那么它可以工作。

如何在render 函数之外使用处理程序来启动具有正确变量值的突变请求?我也很想知道为什么这个构造不起作用并且变量是空的。

【问题讨论】:

  • 你可以试试let { email, password } 而不是const { email, password }
  • @ViswanathLekshmanan:是一样的。
  • &lt;SignIn onClick={(e, p) =&gt; this.handleClick(e, p, request)} /&gt;; 中的 ep 是什么?
  • @ViswanathLekshmanan 它是来自 SignIn 组件的电子邮件和密码,通过 handleClick 处理程序,结合 request 对象用于发起请求。
  • 可以发request()的方法吗

标签: javascript react-apollo apollo-client


【解决方案1】:

我认为这里的问题在于:

this.onClick = this.handleClick.bind(this);

如果绑定不正确,您将不会触发您想要的方法。这应该是:

this.handleClick = this.handleClick.bind(this);

以下实现你想要的。我已经精简了它,因为我对你的 Apollo 实现一无所知,但希望你能明白要点:


// SignIn.jsx

import React, { Component } from "react";

class SignIn extends Component {
  constructor(props) {
    super(props);
    this.handleClick = this.handleClick.bind(this);
    this.state = {
      email: "",
      password: ""
    };
  }

  handleClick = () => {
    this.props.onClick(this.state.email, this.state.password);
  };

  handleEmailChange = e => {
    this.setState({ email: e.target.value });
  };

  handlePasswordChange = e => {
    this.setState({ password: e.target.value });
  };

  render() {
    return (
      <div>
        <input
          id="email"
          name="email"
          autoComplete="email"
          autoFocus
          value={this.state.email}
          onChange={this.handleEmailChange}
        />

        <input
          name="password"
          type="password"
          id="password"
          autoComplete="current-password"
          value={this.state.password}
          onChange={this.handlePasswordChange}
        />

        <button onClick={this.handleClick}>Click Me</button>
      </div>
    );
  }
}

export default SignIn;

// App.jsx

import React, { Component } from "react";
import ReactDOM from "react-dom";

import SignIn from "./SignIn";

class App extends Component {
  constructor(props) {
    super(props);
    this.handleClick = this.handleClick.bind(this);
    this.state = {
      email: "",
      password: ""
    };
  }

  handleClick(e, p, request) {
    console.log("Requesting: ", request);
  }

  render() {
    const { email, password } = this.state;
    const request = "Your Apollo Request";
    console.log("render", email, password); // here I see the right state after click
    return (
      <div>
        <SignIn onClick={(e, p) => this.handleClick(e, p, request)} />;
      </div>
    );
  }
}

export default App;

【讨论】:

  • 这不起作用。绑定函数甚至不是必需的,因为我使用箭头函数作为处理程序。该方法正在被触发,但带有 empty 变量。问题可能与 Apollo 突变有关。
  • @Pablo 我想我知道问题出在哪里——在 Apollo 中构建“动态”查询/突变可能很困难。当我有机会更详细地研究它时,我会回复你。
  • 查看我在原帖中的评论
猜你喜欢
  • 2021-10-03
  • 1970-01-01
  • 1970-01-01
  • 2015-04-16
  • 1970-01-01
  • 1970-01-01
  • 2020-12-20
  • 2011-06-21
相关资源
最近更新 更多