首页 > 解决方案 > 如何在 Reactjs 中更改单个按钮的文本

问题描述

我有一个带有批准按钮的工作列表。

预期结果

每当单击 Job 旁边的Approve按钮时,该 Job 应该被批准并且按钮文本应该显示Approved

原始结果

所有按钮的文本都更改为Approved,但只有一个 Job 获得批准,即实际批准的 Job。此外,在页面刷新之前,所有作业的文本都会保持批准。

export default class ProfilePage extends Component {

  constructor() {
    super();
    this.state = {
      allJobs: [],
      loading: true,
      newLoading: false,
      valueApprove: "Approve",
      _id: ""
    };

    this.handleApproveJob = this.handleApproveJob.bind(this);
  }

  componentDidMount() {

    var apiUrl = `http://localhost:5000/admin/pendingJobs`;
    fetch(apiUrl)
      .then(response => {
        return response.json();
      })
      .then(data => {
        let allJobsFromApi = data.PendingJobs.map(job => {
          return {
            jobmainid: job._id,
            companyName: job.companyNane,
            contactPerson: job.contactPerson,
            jobTitle: job.jobTitle,
            jobDescription: job.description,
            jobCategory: job.category.name,
            jobDuration: job.duration,
            descriptionLink: job.descriptionLink,
            status: job.status
          }
        })
        this.setState({ allJobs: allJobsFromApi, loading: false });
      })
      .catch(error => {
        console.log(error);
      })
  }

  handleApproveJob(e) {
    this.setState({
      newLoading: true
    })
    e.preventDefault();
    var jobId = e.target.getAttribute('jobId');
    console.log(jobId);
    const job = {
      approvedJobId: jobId
    };
    approveJob(job).then((res, err) => {
      if (res) {
        this.setState({
          newLoading: false,
          valueApprove: "Approved"
        })
      } else {
        this.setState({
          loading: false,
          message: "some error occured"
        })
      }
    })
  }

render() {
    const { newLoading, valueApprove } = this.state;
    return (
            <div className="tile-body">
              {loading ? <div className="col-md-4 offset-md-4"><img src= 
                 {LoadingSpinner} /></div> : <table
                   className="table table-hover table-bordered table-responsive"
                    id="sampleTable"
                    style={{ border: "none" }}
                    >
                      <thead>
                        <tr>
                          <th>Company Name</th>
                          <th>Contact Person At Company</th>
                          <th>Job Title</th>
                          <th>Job Description</th>
                          <th>Job Description Link</th>
                          <th>Category</th>
                          <th>Duration</th>                          
                          <th>Edit</th>
                          <th>Approve</th>
                        </tr>
                      </thead>
                      <tbody>
                        {this.state.allJobs.map((job) =>
                          <tr key={job.jobmainid}>
                            <td>{job.companyName}</td>
                            <td>{job.contactPerson}</td>
                            <td>{job.jobTitle}</td>
                            <td>{job.jobDescription}</td>                            
                            <td>
                              <a href={job.descriptionLink} target="_blank">{job.descriptionLink}</a>
                            </td>
                            <td>{job.jobCategory}</td>
                            <td>{job.jobDuration}</td>
                            <td>
                              <Link to={"/admin/editJob/" + job.jobmainid}>
                                <button className="btn btn-warning">Edit</button>
                              </Link>
                            </td>
                            <td>
                              <button
                                type="submit"
                                className="btn btn-success"
                                jobId={job.jobmainid}
                                onClick={this.handleApproveJob}
                              >
                                { newLoading ? <ButtonLoading /> : valueApprove }
                          </button>
                            </td>
                          </tr>

                        )}

                      </tbody>
                    </table>}
                  </div>


The code for aproveJob() function
//Approve Job
export const approveJob = job => {
    return axios.post("http://localhost:5000/admin/approveJob", {
        _id: job.approvedJobId
    })
        .then(response => {
            return response.data;
        })
        .catch(err => {
            console.log(err);
        });
}

标签: reactjs

解决方案


现在,您只存储一个具有已批准状态的变量。相反,我们需要每个按钮一个。

您可以执行类似以下代码的操作。

  1. 从服务器获取数组作业后注入一个值approved: false
  2. 在按钮上单击查找并更新您所在州的该项目approved: true

我不确定下面的代码是否运行,但它会为您指明正确的方向。

import React, { Component } from 'react'
import { Link } from 'react-router-dom'

export const approveJob = (job) => {
  return fetch('http://localhost:5000/admin/approveJob', {
    _id: job.approvedJobId
  })
    .then((response) => {
      return response.data
    })
    .catch((err) => {
      console.log(err)
    })
}

export default class ProfilePage extends Component {
  constructor(props) {
    super(props)
    this.state = {
      allJobs: [],
      loading: true,
      newLoading: false
    }

    this.handleApproveJob = this.handleApproveJob.bind(this)
  }

  componentDidMount() {
    const apiUrl = `http://localhost:5000/admin/pendingJobs`
    fetch(apiUrl)
      .then((response) => {
        return response.json()
      })
      .then((data) => {
        const allJobsFromApi = data.PendingJobs.map((job) => {
          return {
            jobmainid: job._id,
            companyName: job.companyNane,
            contactPerson: job.contactPerson,
            jobTitle: job.jobTitle,
            jobDescription: job.description,
            jobCategory: job.category.name,
            jobDuration: job.duration,
            descriptionLink: job.descriptionLink,
            status: job.status,
            approved: false
          }
        })
        this.setState({ allJobs: allJobsFromApi, loading: false })
      })
      .catch((error) => {
        console.log(error)
      })
  }

  handleApproveJob(e, index) {
    e.preventDefault()

    this.setState({
      newLoading: true
    })
    const jobId = e.target.getAttribute('jobId')
    console.log(jobId)
    const job = {
      approvedJobId: jobId
    }
    approveJob(job).then((res) => {
      if (res) {
        const newAllJobs = this.state.allJobs
        newAllJobs[index].approved = true
        this.setState({
          newLoading: false,
          valueApprove: 'Approved',
          allJobs: newAllJobs
        })
      } else {
        this.setState({
          loading: false,
          message: 'some error occured'
        })
      }
    })
  }

  render() {
    const { loading, newLoading, valueApprove, allJobs } = this.state
    return (
      <div className="tile-body">
        {loading ? (
          <div className="col-md-4 offset-md-4">
            <img src={LoadingSpinner} />
          </div>
        ) : (
          <table
            className="table table-hover table-bordered table-responsive"
            id="sampleTable"
            style={{ border: 'none' }}
          >
            <thead>
              <tr>
                <th>Company Name</th>
                <th>Contact Person At Company</th>
                <th>Job Title</th>
                <th>Job Description</th>
                <th>Job Description Link</th>
                <th>Category</th>
                <th>Duration</th>
                <th>Edit</th>
                <th>Approve</th>
              </tr>
            </thead>
            <tbody>
              {allJobs.map((job, index) => (
                <tr key={job.jobmainid}>
                  <td>{job.companyName}</td>
                  <td>{job.contactPerson}</td>
                  <td>{job.jobTitle}</td>
                  <td>{job.jobDescription}</td>
                  <td>
                    <a href={job.descriptionLink} target="_blank">
                      {job.descriptionLink}
                    </a>
                  </td>
                  <td>{job.jobCategory}</td>
                  <td>{job.jobDuration}</td>
                  <td>
                    <Link to={'/admin/editJob/' + job.jobmainid}>
                      <button className="btn btn-warning">Edit</button>
                    </Link>
                  </td>
                  <td>
                    <button
                      type="button"
                      className="btn btn-success"
                      jobId={job.jobmainid}
                      onClick={(e) => this.handleApproveJob(e, index)}
                    >
                      {newLoading ? <ButtonLoading /> : valueApprove}
                    </button>
                  </td>
                </tr>
              ))}
            </tbody>
          </table>
        )}
      </div>
    )
  }
}

推荐阅读