Sei sulla pagina 1di 6

21/08/2019 Angular 4 - Datatable isn't reloading data correctly.

· Issue #1146 · l-lin/angular-datatables · GitHub

l-lin / angular-datatables

Dismiss
Join GitHub today
GitHub is home to over 40 million developers working together to host and
review code, manage projects, and build software together.

Sign up

Angular 4 - Datatable isn't reloading data correctly. #1146 New issue

Closed iCrash91 opened this issue on 1 Dec 2017 · 20 comments

iCrash91 commented on 1 Dec 2017 Assignees

No one assigned
I'm submitting a...
Labels

Angular
[ ] Regression (a behavior that used to work and stopped working in a new release) question
[x ] Bug report
[ ] Feature request
[ ] Documentation issue or request
Projects

None yet

What versions you are using?


Milestone

No milestone

- node version: 6.11.2


- angular version: 4 9 participants
- angular-cli version: 1.2.7
- jquery version: 1.9.1
- datatables version: 1.10.16
- angular-datatables version: 4.4.1

Current behavior

When I load the datatable the first time, everything works propertly, but if I add / edit or delete a new row
using http, the data changes but the table doesn't recognize it. For example, If the table is empty it
shows "No data available in table", after I push a new row to my array, I can see the row but also the "no
data available" message,in the footer still displays "showing 0 to 0 of 0 entries" and I can't use the
search bar to find the new row because it says no results. I tried using the rerender method as shown in
the documentation, but after the rerender the new data disappear.

First time the table is loaded

After the data is addes

Expected behavior
https://github.com/l-lin/angular-datatables/issues/1146 1/6
21/08/2019 Angular 4 - Datatable isn't reloading data correctly. · Issue #1146 · l-lin/angular-datatables · GitHub
The table should recognize the changes made to the data in the table.

Minimal reproduction of the problem with instructions

This is my component

export class DrillsComponent implements OnInit {


public drills: Array<Drill>;
public addDrill = new Drill();
dtOptions: any = {};
dtTrigger: Subject<any> = new Subject();

constructor(private drillService: DrillService ) {


this.drill = [];
this.getDrills();
this.dtOptions = {
pagingType: 'full_numbers',
retrieve: true,
};
}

//function to load data from API


getDrills() {
this.drillService.getDrills()
.subscribe(
data => {
for (let drill of data) {
this.drills.push(new Drill(drill))
this.dtTrigger.next();
}
},
error => {
console.log(error)
}
);
}
//Functin to add new data
saveDrill(){
this.drillService.saveDrill(this.addDrill).subscribe(
data => {
this.drills.push(new Drill(data))
},
error => {
console.log(error)
});
}

Methods in my service to send and load the data

//Get data from api


getDrills() {
return this.http.get(this.apiUrl).map(res => res.json());
}
//Save data in API
saveDrill(data) {
return this.http.post(this.apiUrl,data).map(res => res.json());
}

Template

<table class="table" width="100%" [dtOptions]="dtOptions" [dtTrigger]="dtTrigger" datatab


<thead>
<tr>
<th> Code</th>
<th> Name</th>
<th> Location</th>
<th> Operation Time</th>
<th> Status</th>
</tr>
</thead>
<tbody>
<tr *ngFor="let drill of drills" >
<td >{{drill.code}}</td>
<td>{{drill.name}}</td>
<td>{{drill.location}}</td>
<td>{{drill.operation_time}}</td>
<td>{{drill.status}}</td>
</tr>

https://github.com/l-lin/angular-datatables/issues/1146 2/6
21/08/2019 Angular 4 - Datatable isn't reloading data correctly. · Issue #1146 · l-lin/angular-datatables · GitHub
</tbody>
</table>

iCrash91 changed the title Datatable isn't reloading data correctly. Angular 4 - Datatable isn't
reloading data correctly. on 1 Dec 2017

l-lin commented on 3 Dec 2017 Owner

Angular and DataTables do not work on the same "data", ie any changes on Angular won't be impacted
on DataTables. After you add your row, you need to rerender your DataTable so that DataTables
acknowledges the changes.

Unfortunately, it's not really smooth and performant as it will rerender the whole DataTables instead of
just adding/removing rows... I don't have any alternative solution.

l-lin added Angular question labels on 3 Dec 2017

Korigoth commented on 8 Dec 2017

this is a problem for our project, many tables need to play with dynamic data, so we decided to stop
using this. the glitch it's making while rerendering is not a good user experience.

so datatables must be used with static data only.

l-lin commented on 11 Dec 2017 Owner

Another approach is to not use the angular renderer, but using the DataTable's API to add rows. This
way, your table will be fully updated.

s3rkan commented on 12 Dec 2017 • edited

you will need to destroy your datatable before you run this.dtTrigger.next(); when data is updated ->

this.dtElement.dtInstance.then((dtInstance: DataTables.Api) => {


// first destroy table
dtInstance.destroy();
// get your data function call here
});

might do the trick...

update: i use it this way in my application works just fine when rows added or deleted the it will rerender
table as written in above comments not that "beautiful" experience..

Korigoth commented on 16 Dec 2017

it doesnt work for me

dtTrigger: Subject = new Subject();


@ViewChild('lacuneTable') lacuneTable: DataTableDirective;

this.lacuneTable.dtInstance.then dtInstance is null each time

i have many datable in my component and i need to specify the one that is dynamic

how can i do it?

s3rkan commented on 16 Dec 2017

Could you post a plunker or something similar?

Korigoth commented on 18 Dec 2017 • edited

https://github.com/l-lin/angular-datatables/issues/1146 3/6
21/08/2019 Angular 4 - Datatable isn't reloading data correctly. · Issue #1146 · l-lin/angular-datatables · GitHub

i don't really know how to build up a project for Angular5 + Datatables in plunkr sorry but here is the
code

HTML

<table datatable [dtOptions]="options" [dtTrigger]="trigger" class="table table-sm


table-bordered table-hover table-striped">
<thead>
<tr>
<th>Numéro</th>
<th>Description</th>
</tr>
</thead>

<tbody>
<tr *ngFor="let lacune of lacunes" class="table-row-clickable"
(click)="voirLacune(lacune)">
<td>{{lacune.numero}}</td>
<td [innerHTML]="lacune.description"></td>
</tr>
</tbody>
</table>

Component

trigger = new Subject<any>();

ngOnInit(): void {
this.route.params.subscribe(params => {
forkJoin(
this.appreciationsService.obtenirListe(),
this.recommandationsService.obtenir(+params['id'])
).subscribe(reponse => {
this.recommandation = reponse[1];
this.lacunes = this.recommandation.lacunes;
this.trigger.next(); // This doesnt render the datatables nor does it show
sort arrow on table and it doesnt add datatables class to the table
});
});
}

Korigoth commented on 18 Dec 2017 • edited

ngAfterViewInit doesn't work for us, because we are loading data async and the AfterViewInit were
called before data were back from server.

the this.trigger.next) in ngOnInit doesn't work either, while debugging the datables pluggin doesnt
receive the next() event.

so we ended replacing the this.trigger.next() to

setTimeout(function() {
this.trigger.next();
}.bind(this));

and now it's working as expected

l-lin commented on 29 Dec 2017 Owner

For information, you can use this plnkr template to demonstrate your issue.

silentFred commented on 17 Jan 2018

@s3rkan how did you get a reference to your dtElement?

sebastian-zarzy… commented on 2 Feb 2018

https://github.com/l-lin/angular-datatables/issues/1146 4/6
21/08/2019 Angular 4 - Datatable isn't reloading data correctly. · Issue #1146 · l-lin/angular-datatables · GitHub

I'm kind of confused. So what this library actually does "in Angular way"? It seems like nothing else than
a glorified wrapper over DataTable's API, but what's the point if it cannot properly rerender the data
angular ngFor is generating? That destroy/create technique is hack at best. Is there no other way?

Korigoth commented on 4 Feb 2018

it seems that the original library is using the same way to regenerate the data if you dont use the column
data way.

l-lin commented on 4 Feb 2018 Owner

It seems like nothing else than a glorified wrapper over DataTable's API

It is just a wrapper over DataTable's API.

what's the point if it cannot properly rerender the data angular ngFor is generating? That
destroy/create technique is hack at best.

Unfortunately, it's been quite a time since I "touched" the frontend development (because it's moving so
fast and it's not really my "expertise" and I don't have much time this year), that's why there are no
improvement in this wrapper for quite some time... But, pull requests are always welcome :)

Korigoth commented on 4 Feb 2018

And you can check the code it's pretty straight forward.

xts-velkumars commented on 4 May 2018

i'm also having the same problem, reloading the data is not binding properly.
Its disappeared immediately

jagdishjadeja commented on 14 Jun 2018

if it can be used only with static data then it should be given with big heading on front page of it

pktron commented on 28 Jul 2018 • edited

Same here... my scenario:


Im using datatables on a child component, and i have a change detection using DoCheck
When i rerender the new row get deleted even from the dom...

@ViewChild(DataTableDirective)
dtElement: DataTableDirective;

differ: any;
first: Boolean = true;

@Input() labels: string[] = ['Label 1', 'Label 2', 'Label 3'];


@Input() rows: string[][] = [
['Test 1', 'Test 2', 'Test 3'],
['Prueba 1', 'Prueba 2', 'Prueba 3']
];

dtOptions: DataTables.Settings = {};


dtTrigger: Subject<any> = new Subject();

constructor(private _iterableDiffers: IterableDiffers ) {


this.differ = this._iterableDiffers.find([]).create(null);
this.dtOptions = {
pageLength: 20
};
}

https://github.com/l-lin/angular-datatables/issues/1146 5/6
21/08/2019 Angular 4 - Datatable isn't reloading data correctly. · Issue #1146 · l-lin/angular-datatables · GitHub
ngDoCheck() {
const change = this.differ.diff(this.rows);
if (change && !this.first) {
this.rerender();
}
this.first = false;
}

ngAfterViewInit(): void {
this.dtTrigger.next();
}

ngOnDestroy(): void {
this.dtTrigger.unsubscribe();
}

rerender(): void {
this.dtElement.dtInstance.then((dtInstance: DataTables.Api) => {
// Destroy the table first
dtInstance.destroy();
// Call the dtTrigger to rerender again
// this.dtTrigger.next();
});
}

It is weird because if i dont destroy the datatable the row shows, but i cant search or use the datatable
but when i destroy it it the destroy the new data and change it to where the datatable was initialized.

Korigoth commented on 28 Jul 2018

@pktron I've found a way to make it work i think for you!

put everything that is in your rerender() method in a setTimeout

rerender(): void {
setTimeout(() => {
// put rest of the code here
});
}

pktron commented on 30 Jul 2018

I solved it using that approach @Korigoth thanks a lot!

Korigoth commented on 7 Aug 2018

@pktron np ;) it doesn't solve all the problem but it help in 95% of the case !

l-lin closed this on 25 Aug 2018

https://github.com/l-lin/angular-datatables/issues/1146 6/6

Potrebbero piacerti anche