0

I wrote an angular datatable which fetches and populates the table with data from server. Code is given below:
HTML:

<table
            class="table display table-striped table-hover table-bordered row-border hover responsive nowrap"
            datatable
            [dtOptions]="dtOptions"
            datatable=""
            #dataTable
            id="issueTable"
          >
            <thead class="headColor">
              <!-- <tr>
                <th>Action</th>
              </tr> -->
            </thead>
            <tbody>
              <!-- <tr>
                <td><button class="btn btn-primary btnColor" (click)="buttonInRowClick($event)">View</button></td>
              </tr> -->
            </tbody>
          </table>  

angular code:

import { Component, OnInit, Renderer, AfterViewInit, ViewChild } from '@angular/core';
import { Router, RouterLink } from '@angular/router';
import { routerTransition } from '../../router.animations';

import { DataTableDirective } from 'angular-datatables';

import 'datatables.net';
import 'datatables.net-bs4';

window['jQuery'] = window['$'] = $;

@Component({
    selector: 'app-charts',
    templateUrl: './issues.component.html',
    styleUrls: ['./issues.component.scss'],
    animations: [routerTransition()]
})
export class IssuesComponent implements OnInit {

    @ViewChild(DataTableDirective)
    datatableElement: DataTableDirective;
    message = '';
    title = 'angulardatatables';

    @ViewChild('dataTable') table;
    dataTable: any;

    /**
     * gets settings of data tables
     *
     * @type {DataTables.Settings}
     * @memberof IssuesComponent
     */
    constructor(private router: Router) { }
    dtOptions: DataTables.Settings = {};
    // someClickhandler(info: any): void {
    //     this.message = info.number + '-' + info.assignedto + '-' + info.company;
    //     console.log(this.message);
    // }
    ngOnInit(): void {
        this.dtOptions = {
            pagingType: 'full_numbers',
            pageLength: 15,
            processing: true,
            responsive: true,
            autoWidth: false,
            dom: 'Bfrtip',
            'ajax': {
                url: 'http://localhost:8080/incident-updated',
                type: 'GET',
                dataSrc: 'result',
            },
            columns: [
                {
                    title: 'Incident',
                    data: 'number'
                },
                {
                    title: 'Product',
                    data: 'u_product'
                },
                {
                    title: 'Status',
                    data: 'state'
                },
                {
                    title: 'Created By',
                    data: 'sys_created_by'
                },
                {
                    title: 'Group',
                    data: 'assignment_group'
                },
                {
                    title: 'Category',
                    data: 'u_category'
                },
                {
                    title: 'Updated on',
                    data: 'sys_updated_on'
                },
                {
                    title: null,
                    data: null,
                    render: function(data, type, full) {
                        return '<a class="btn btn-info btn-sm" href=#/>' + 'View' + '</a>';
                      }
                }
            ]
            // ,
            // columnDefs: [
            //     {
            //         targets: -1,
            //         data: null,
            //         defaultContent: '<button>Click!</button>'
            //     }
            // ]
        };
        this.dataTable = $(this.table.nativeElement);
        console.log('table is ==>', this.dataTable);
        $('#issueTable tbody').on('click', 'button', function () {
            const data = this.dataTable.row($(this).parents('tr').data);
            console.log('Data is ==>', data);
        });
    }
    buttonInRowClick(event: any): void {
        event.stopPropagation();
        console.log('Button in the row clicked.');
        this.router.navigate(['/event-viewer']);
    }
    wholeRowClick(): void {
        console.log('Whole row clicked.');
    }
    // ngAfterViewInit() {
    //     this.renderer.listenGlobal('document', 'click', (event) => {
    //         if (event.target.hasAttribute("view-person-id")) {
    //             this.router.navigate(["/person/" + event.target.getAttribute("view-person-id")]);
    //         }
    //     });
    // }
}  

When I run that code, I get this error:

ERROR TypeError: Cannot read property 'replace' of null
    at _fnSortAria (VM1053 scripts.js:16659)
    at jQuery.fn.init.<anonymous> (VM1053 scripts.js:11820)
    at VM1053 scripts.js:17237
    at Function.map (VM1053 scripts.js:456)
    at _fnCallbackFire (VM1053 scripts.js:17236)
    at _fnDraw (VM1053 scripts.js:14107)
    at _fnReDraw (VM1053 scripts.js:14150)
    at _fnInitialise (VM1053 scripts.js:15333)
    at loadedInit (VM1053 scripts.js:11893)
    at HTMLTableElement.<anonymous> (VM1053 scripts.js:11905)  

How do I fix this error?

1 Answer 1

1

I'm not sure about this but I think here is the problem:

{
    title: null,
    data: null,
    render: function(data, type, full) {
        return '<a class="btn btn-info btn-sm" href=#/>' + 'View' + '</a>';
    }
}

Even if you don't use any field inside return, you should put some column name, for example data: 'u_product':

{
    title: null,
    data: 'u_product',
    render: function(data, type, full) {
        return '<a class="btn btn-info btn-sm" href=#/>' + 'View' + '</a>';
    }
}

I recommend you to use the primary key column of the table, maybe in the future it will be useful in the button.

Sign up to request clarification or add additional context in comments.

1 Comment

Got it... Modified that part as { title: 'Action', data: null, render: function(data, type, full) { return '<a class="btn btn-info btn-sm" href=#/>' + 'View' + '</a>'; } } Thank you :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.