0

I am trying to update the state of a component with ReactJS but getting the following error. Error and code provided below.

Potentially unhandled rejection [1] TypeError: Cannot read property 'setState' of undefined

import React from 'react';
import {BootstrapTable, TableHeaderColumn} from 'react-bootstrap-table';

var rest, mime, client;

rest = require('rest');
mime = require('rest/interceptor/mime');

import ParameterDialog from './parameter-dialog';

const parameterTypes = {
    'STRING': 'STRING',
    'BOOLEAN': 'BOOLEAN',
    'INTEGETR': 'INTEGETR',
    'DECIMAL': 'DECIMAL'
};

const categoryAvailable = {
    'POS': 'POS'
};

const options = {
    noDataText: 'No parameters founds.'
}

function enumFormatter(cell, row, enumObject) {
    return enumObject[cell];
}

export default class ParameterContainer extends React.Component {

    constructor(props) {
        super(props);
        this.state = { parameters: [] };
        this.client = rest.wrap(mime);
    }

    fetchFromApi() {
        this.client({ path: '/api/parameters' }).then(function(response) {
            this.setState({parameters: response});
        });
    }

    componentDidMount() {
        this.fetchFromApi();
    }

    render() {
        return (
            <div>
                <h2>Parameters</h2>
                <ParameterDialog />
                <BootstrapTable data={this.state.parameters} options={options} pagination>
                    <TableHeaderColumn isKey dataField='id'>ID</TableHeaderColumn>
                    <TableHeaderColumn dataField='category' filterFormatted dataFormat={enumFormatter} formatExtraData={categoryAvailable}
                        filter={{type: 'SelectFilter', options: categoryAvailable}}>Category</TableHeaderColumn>
                    <TableHeaderColumn dataField='subCategory'>Sub Category</TableHeaderColumn>
                    <TableHeaderColumn dataField='parameter' filter={ { type: 'TextFilter', delay: 500 } }>Parameter</TableHeaderColumn>
                    <TableHeaderColumn dataField='type' filterFormatted dataFormat={enumFormatter} formatExtraData={parameterTypes}
                                       filter={{type: 'SelectFilter', options: parameterTypes}}>Type</TableHeaderColumn>
                    <TableHeaderColumn dataField='roles'>Roles</TableHeaderColumn>
                </BootstrapTable>
            </div>
        )
    }
}
Vikas Sardana
  • 1,593
  • 2
  • 18
  • 37
greyfox
  • 6,426
  • 23
  • 68
  • 114
  • Please search before asking questions – Andy Ray Feb 19 '17 at 20:04
  • if you're using babel you can use https://babeljs.io/docs/plugins/transform-es2015-arrow-functions/ and then you don't need to bind your arrow functions anymore – programmingheadaches Apr 16 '17 at 19:00
  • while using 'this' keyword in callback we need make sure who is calling this callback. Here To acess the lexical scope you need to arrow function or you can bind the function. For better understanding you can look into lexical scope and Dynamic scope – zakir Feb 19 '19 at 09:51

3 Answers3

0

Problem seems to be with changing context of this, you created Promise and and trying to change its state. this.fetchFromApi.bind(this)

Felix
  • 55
  • 9
0

You need to use arrow function if you are using stage-0 babel transpiler.

class ParameterContainer{
  fetchFromApi = () => {

  }
}

otherwise you can bind fetchFromApi function in constructor to this.

constructor(){
   this.fetchFromApi = this.fetchFromApi.bind(this)
}
Zeel Shah
  • 462
  • 6
  • 15
-1

Edited my answer:

if you're using babel you can use https://babeljs.io/docs/plugins/transform-es2015-arrow-functions/ and then you don't need to bind your arrow functions anymore