【问题标题】:Not able to submit form - ReactJs, Node.js无法提交表单 - ReactJs、Node.js
【发布时间】:2019-06-26 10:12:22
【问题描述】:

我正在尝试学习 ReactJs 和 NodeJs,这是我第一次同时使用它们。 我有一个应用程序,其中使用 NodeJs 和 Express 创建后端,并在 ReactJs 中创建前端。

服务器正常工作,所有端点都使用 Postman 进行了测试。 我正在尝试通过创建新项目来连接前端和后端。

这是一个简单的 CRUD 应用程序,它应该创建、更新和删除酒店的房间。

我有一个父组件App.js 和两个子组件。 一个子组件是Admin.js,用户可以在其中更改房间详细信息,另一个子组件是LandingPage.js,应显示更改。

App.js

export default class App extends React.Component {

    constructor(props) {
      super(props);

      this.state = {
        initialTitle: '',
        initialDescription: '',
        initialPrice: ''
      }
    }

    onChangeTitle(newTitle) {
      this.setState({
        initialTitle: newTitle
      });
    }

    onChangeDescription(newDescription) {
      this.setState({
        initialDescription: newDescription
      });
    }

    onChangePrice(newPrice) {
      this.setState({
        initialPrice: newPrice
      });
    }

    onSubmit(e) {
      e.preventDefault();
      const obj = {
        initialTitle: this.state.initialTitle,
        initialDescription: this.state.initialDescription,
        initialPrice: this.state.initialPrice
      };
      axios.post('http://localhost:27017/admin/add', obj)
        .then(res => console.log(res.data));

      this.setState({
        initialTitle: '',
        initialDescription: '',
        initialPrice: ''
      })
    }
    render() {
        return (

            <div>
            <Route path = "/" exact component = {LandingPage}/>
            <Route path = "/admin" component = {() =>
              <Admin 
              initialTitle = {
                this.state.initialTitle
              }
              initialDescription = {
                this.state.initialDescription
              }
              initialPrice = {
                this.state.initialPrice
              }
              changeTitle = {
                this.onChangeTitle.bind(this)
              }
              changeDescription = {
                this.onChangeDescription.bind(this)
              }
              changePrice = {
                this.onChangePrice.bind(this)
              }
              onSubmit = {
                this.onSubmit
              }
              />}/ >

Admin.js

我正在使用 Boostrap 4 模态。当我点击按钮时弹出模式,我应该插入房间详细信息并点击保存按钮。

class Admin extends React.Component {

  constructor(props) {
    super(props);

    this.state = {
      title: props.initialTitle,
      description: props.initialDescription,
      price: props.initialPrice

    }
  }

  onFormSubmit() {
    console.log("save");
    this.props.changeTitle(this.state.title)
    this.props.changeDescription(this.state.description)
    this.props.changePrice(this.state.price)
  }


  onHandleTitleChange(event) {
    this.setState({
      title: event.target.value
    });
  }

  onHandleDescriptionChange(event) {
    this.setState({
      description: event.target.value
    });
  }

  onHandlePriceChange(event) {
    this.setState({
      price: event.target.value
    });
  }


  render() {
    return (
          <div>  

      <button type="button" data-toggle="modal" data-target="#createModal" class="btn btn-      primary btn-lg btn-block mb-5">Add new room</button>

          </div>
          <div className="modal-body">
            <form onSubmit={this.onFormSubmit}>
              <div className="form-group">
                <label htmlFor="title" className="col-form-label">Title:</label>
                <input 
                type="text" 
                value={this.state.title} 
                onChange{(event)=>this.onHandleTitleChange(event)} 
                />
              </div>
              <div className="form-group">
                <label htmlFor="message-text" className="col-form-label">Description:</label>
                <textarea 
                type="text" 
                value={this.state.description} 
                onChange{(event)=>this.onHandleDescriptionChange(event)}"></textarea>
              </div>
              <div className="form-group">
                <label htmlFor="title" className="col-form-label">Price:</label>
                <input 
                type="text" 
                value={this.state.price} 
                onChange={(event)=>this.onHandlePriceChange(event)} />
              </div>
            </form>
          </div>
          <div className="modal-footer">
            <button type="button" className="btn btn-secondary"
            data-dismiss="modal">Close</button>
            <button data-backdrop="false" type="button" 
            className="btn btn-primary">Save</button>
          </div>
        </div>
      </div>
    </div>
  </div>
    )
  }

}
export default requireAuth(Admin);

当我点击保存按钮时没有任何反应,我没有收到任何错误,并且我的数据没有保存在数据库中。

后端代码

room.route.js

// Defined store route
roomRoutes.route('/add').post(function (req, res) {
    let room = new Room(req.body);
    room.save()
      .then(room => {
        res.status(200).json({'room': 'room in added successfully'});
      })
      .catch(err => {
      res.status(400).send("unable to save to database");
      });
  });

index.js

//DB setup
mongoose.connect("mongodb://localhost:27017/hotel", { useNewUrlParser: true });

//App setup
app.use(morgan('combined')); //every incoming request is passed to morgan and bodyParser
app.use(cors());
app.use(bodyParser.json({type: '*/*'})); //morgan and bodyParser are like middleware in express

app.use('/admin', roomRoute);
router(app);

//Server setup
const port = process.env.PORT || 3090;
//create http server who knows how to recieve request and send to app
const server = http.createServer(app);
server.listen(port);
console.log('server listenining on ', port);

非常感谢任何建议。

【问题讨论】:

  • “保存”按钮应该在 HTML 表单标签内,并且应该是“提交”类型
  • 如果您将所有逻辑提升到应用级别,您的应用将很快无法维护
  • @Dominic 好的,对你来说有什么好的解决方案?我认为这是一个很好的方法,也是使用父组件在子组件之间传递数据的方法。

标签: javascript node.js reactjs


【解决方案1】:

在你的函数 onFormSubmit 到管理组件中,你还需要调用你的 onSubmit 属性。

onFormSubmit() {
    console.log("save");
    this.props.changeTitle(this.state.title)
    this.props.changeDescription(this.state.description)
    this.props.changePrice(this.state.price)
    this.props.onSubmit()
  }

【讨论】:

  • 我添加了它,但还是一样,什么都没有显示:/ 我忘了提到在服务器端和客户端的身份验证也已设置。因此,我以用户更改房间详细信息的身份登录并保存。你认为这会改变什么吗?我对此真的很陌生
  • 而且console.log("save"); 永远不会显示在控制台中,因此永远不会输入函数
【解决方案2】:

你需要调用App 组件的onSubmit 方法才能使其工作。您将它作为道具传递给Admin 组件,但您根本没有在Admin 组件中使用。 在您的Admin 组件的onFormSubmit 方法调用this.props.onSubmit 将调用发送到App 组件的onSubmit 方法,然后只有它会调用您的后端。

将您的 onFormSubmit 方法更改为:

onFormSubmit() {
    console.log("save");
    this.props.changeTitle(this.state.title)
    this.props.changeDescription(this.state.description)
    this.props.changePrice(this.state.price)
    this.props.onSubmit();
}

是的,在 Admin 组件中将按钮类型更改为 submit 试试看,让我知道。希望能帮助到你!!

【讨论】:

  • 我很抱歉,但我是新手,我不太明白该怎么做,你能写代码吗?
猜你喜欢
  • 2018-06-20
  • 2021-09-08
  • 1970-01-01
  • 2020-09-02
  • 1970-01-01
  • 2012-01-27
  • 2018-10-12
  • 2013-01-25
相关资源
最近更新 更多