从ReactJS调用javascript函数

3

我是javascript和reactJS的新手,遇到了麻烦。我有一个javascript文件,其中进行了REST调用。文件如下所示:

var data;
function getDataRequest() {
 const request = new XMLHttpRequest();
    request.open('GET', "localhost:8080/getData", true);
    request.onload = function () {
        var data = JSON.parse(this.response);
        if (request.status >= 200 && request.status < 400) {
            products = data;
        } else {
            console.log('error');
        }
    };
    request.send();
}
var getDataList = function() {
    getDataRequest();
    return data;
};
getDataList();

包含React组件的文件如下所示:

var = data;
class Datas extends React.Component {

    render() {
        data = this.getDataList;
        return (
            <DataTable data={data} />
        );
    }
}
export default Products;

问题在于React组件中的数据仍然是“undefined”。我在不同的文件中进行rest调用,因为我想从多个React组件中调用rest调用。

你需要创建一个状态,并编写一个方法来更新该状态。然后从不同的文件中导出函数并在组件中导入它。将状态变异方法作为回调传递给导入的函数,并从那里调用它。这就是如何连接所有异步函数的方法。 - Arup Rakshit
你有一个名为Datas的类,然后默认导出Products。这难道不是整个文件吗? - rrd
没有 this.getDataList。那么 products = data; 是什么意思?products 是什么?它在其他地方都没有被定义或使用过。 - user5734311
应该是一个对象列表,包含id、描述和名称,例如: { "id": 1, "name": "Object0", "description": "desc1" }, { "id": 2, "name": "Object1", "description": "desc2" }, { "id": 3, "name": "Object2", "description": "desc2" } - Catalin
可能是如何返回异步调用的响应的重复问题。 - Mayank Shukla
在数据中,我无法获取getDataList应该返回的值。调用有效,并且请求文件中的数据具有预期值。 - Catalin
4个回答

4

您正在渲染调用中从服务器抓取数据,这是一个非常糟糕的想法。 使用componentDidMount来加载数据,然后将其存储在状态中。

首先,这是您的Data.js

export default {
  getDataList: () => fetch("//localhost:8080/getData").then(res => res.json())
};

在你的组件中,import Data from './Data';,然后执行以下操作:
componentDidMount = () => {  // using this syntax auto-binds 'this'
  Data.getDataList().then(res => {
    this.setState({ data: res });
  });
}

render() {
  return (
    <DataTable data={this.state.data} />
  );
}

1
你需要了解React组件的生命周期。简而言之,有些函数按照特定顺序由React调用。有些在组件渲染之前被调用,有些在之后被调用。在你的情况下,你想在组件渲染后进行API调用。这种情况下适合使用的生命周期方法是componentDidMount。请参考这里以获取更详细的关于组件生命周期方法的信息。
以下是一个示例。请注意,我使用了fetch API而不是XmlHttpRequest。它更加易于使用且是JavaScript的一部分。
class Example extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      loaded: false,
      something: ""
    };
  }

  componentDidMount() {
    fetch("exampleurl")
      .then(response => {
        return response.json();
      })
      .then(json => {
        // perform desired checks etc

        this.setState({
          something: json.someProperty
        });
      });
  }

  render() {
    if (!this.state.loaded) {
      return <div>{"Loading..."}</div>;
    }

    return <div>{this.state.something}</div>;
  }
}

export default Example;

1
我同意你的答案,它是有效的,但我必须多次进行这个和更多的REST调用,我认为从长远来看,只编写一次调用并从另一个文件获取数据更容易。 - Catalin

1
首先,在您的React组件中没有函数getDataList。 其次,如果您想从React组件中调用getDataList,请导出或使您的函数成为全局函数。您可以使用:
window.getDataList = function() {
    getDataRequest();
    return data;
};

在你的React组件中,你可以轻松调用window.getDataList()


0

你需要向泛型函数传递一个回调函数来更新状态

function getDataRequest(callback) { // here
    const request = new XMLHttpRequest();
    request.open('GET', "localhost:8080/getData", true);
    request.onload = function () {
        var data = JSON.parse(this.response);
        if (request.status >= 200 && request.status < 400) {
            callback(data) // here
        } else {
            console.log('error');
        }
    };
    request.send();
}

你需要在 componentDidMount 中创建一个状态并触发调用,这应该在第一次渲染之后进行。
export default class Datas extends React.Component {

    state = {
        data: null // or [] ?
    }

    componentDidMount(){
        const callback = (value) => {
            this.setState({
                data: value
            })
        }
        this.getDataList(callback);
    }

    render() {
        const {
            data
        } = this.state;

        return (
            <DataTable data={data} />
        );
    }
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接