Sankaranarayanan
Sankaranarayanan

Reputation: 111

ag-grid gridOptions.api undefined in angular 2

I am trying ag-grid in angular2 with typescript, for some reasons I am not able to use the ag-grid APIs, getting undefined error.,

here is the code:

import { AgRendererComponent } from 'ag-grid-ng2/main';
import { GridOptions, RowNode } from 'ag-grid/main';
import { GridOptionsWrapper } from 'ag-grid/main';
import { GridApi } from 'ag-grid/main';

public gridOptions: GridOptions;

/**
 * Constructor
 */
constructor()
{
    this.gridOptions = <GridOptions>{};

    alert(this.gridOptions);
    alert(this.gridOptions.api); // *** getting undefined  ***
    
    
    this.gridOptions = <GridOptions>{
        columnDefs: this.columnDefs(),
        rowData: this.rowData,
        onSelectionChanged: this.onSelectionChanged,
        groupSelectsChildren: true,
        suppressRowClickSelection: true,

        rowSelection: 'multiple',
        enableColResize: true,
        enableSorting: true,
        rowHeight: 45}
    
}

Please advise, Thanks

Updated with code in comment below

onGridReady() {
    console.log(this.gridOptions.api); // here it work
    this.selectedRows = this.gridOptions.api.getSelectedRows();
    console.log(this.selectedRows);
}

private testClick(event): void {
    try {
        console.log(this.gridOptions.api); // here gives error
        this.selectedRows = this.gridOptions.api.getSelectedRows();
        console.log(this.selectedRows); //getting error saying undefined
    }
}

Upvotes: 11

Views: 45882

Answers (6)

Maxx Garcia
Maxx Garcia

Reputation: 11

I was looking for an answer on this while using AngularJS. For anyone else who ends up in the same issue as me (though it was not an AngularJS specific issue), I found that I was not calling the table correctly in the HTML. Since the table was never being called, the api was never getting set up and gridReady was never running. Syntax I used that worked:

<div class="table-body">
  <div ag-grid="$ctrl.gridOptions" class="ag-theme-fresh ag-grid-container"></div>
</div>

Upvotes: 1

pradeep ponduri
pradeep ponduri

Reputation: 11

I was using vue.js Had same issue. But when I included :gridOptions="gridOptions" in my ag-grid-vue component that solved my problem

Upvotes: 0

mounds
mounds

Reputation: 1383

Two issues...

First ,as others have mentioned, initialise a reference to the grid api in onGridReady like so

onGridReady(params) {
    this.gridApi = params.api;
}

Secondly, when ag-grid calls one of your provided handlers (E.g. rowClicked), this is no longer your angular component instance, so in your testClick() method this.gridOptions === undefined.

To access properties of your angular component in an AgGrid Event callback you should pass this via GridOptions.context like this:

this.gridOptions = <GridOptions>{
     context: {parentComponent: this},
     ...other lines

AgGrid's events (generally) return a reference to this context object in the Event params..

rowClicked(rowClicked: RowClickedEvent) {
    const localGridApiRef = rowClicked.context.parentComponent.gridApi;

    // do stuff with the grid api...
    const selectedRows = localGridApiRef.getSelectedRows();
};

Note: I'm not sure how you used testClick() but my rowClicked() would be interchangeable I expect...

Note 2 - The GridApi is actually a property of RowClickedEvent, so while getting it via the context object as shown is superfluous, it illustrates the point that accessing properties/methods of your angular component in an ag grid event can be done via AgGridEvent's context property.

Upvotes: 12

Guenther
Guenther

Reputation: 433

Try this:

export class MyComponent implements OnInit {
  selected = () => console.log('ID: ', this.gridOptions.api.getSelectedRows()[0].id);

  gridOptions: GridOptions = {
    columnDefs: [
        {headerName: 'ID', field: 'id', width: 80},
        { ... }
    ],
    rowSelection: 'single'
  }

  ngOnInit() {
    this.gridOptions.rowData = this.gridData;
    this.gridOptions.onSelectionChanged - this.selected;
  }

It worked for me!

Upvotes: 0

Sean Landsman
Sean Landsman

Reputation: 7179

The gridOptions api will be set and ready to use once the grid's gridReady event has been called.

At the line you're testing for it, gridOptions is just an empty Object, and even after you do this:

this.gridOptions = <GridOptions>{
     columnDefs: this.columnDefs(),
     ...other lines

It still won't have the api available - hook into the gridReady or angular's ngOnInit events and you'll be able to invoke the api safely.

Upvotes: 7

Sefa
Sefa

Reputation: 8992

It's because of component lifecycles. In constructor it's not initialized yet. (I'm assuming you assigned gridOptions object to your grid properly.)

Try using it in

ngOnInit() { 
    console.log(this.gridOptions.api)
}

From the documentation

ngOnInit Initialize the directive/component after Angular first displays the data-bound properties and sets the directive/component's input properties.

Get more info about lifecycles here.

Upvotes: 1

Related Questions