Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

In Angularjs, how to update table data after deleting a row from it

I am using the angularjs to call Asp.net Web API. After I delete a row from the table?

I also did not find the solution in w3schools.

My HTML code

 <tr ng-repeat="user in users | filter: search">
     <td>{{ user.Id }}</td>
     <td>{{ user.FullName }}</td>
     <td>{{ user.Mobile }}</td>
     <td>{{ user.Birthdate }}</td>
     <td>{{ user.Gender }}</td>
     <td>{{ user.AcademicLevel }}</td>

     <td>

My Angularjs code

$scope.DeleteUser = function (id) {
    UserID = $scope.users[id].Id;
    $http.delete('/api/users/' + UserID).success(function (data) {
       (function (data) {
        $scope.error = "error " + data;
    });

}

I searched in Stackoverflow, I found some of these where they did not work for me, they confused me.

$scope.refresh()
$scope.apply();
like image 818
Diamond Avatar asked Jun 15 '15 14:06

Diamond


People also ask

How to add/delete table row (AngularJS 1*)?

Add/Delete Table Row (AngularJS 1.*) If the rows are created using JSON data (companies in the example below), following code adds a row to the existing table. The addRow is a method invoked by the form submission. The directive ng-click is used in each row. The ng-click invokes the method removeRow whose code is represented below. <!--

How do I expand and collapse a table in angular?

Also, check how to add extra rows on the Angular Material table and implement Expand/ Collapse functionality by clicking inside each row and multiple rows by clicking on the master button. The master button will toggle expand/ collapse on multiple rows …

How to do operations on table rows in Angular Material?

To do these operations on table rows, we’ll use the Dialog component on Angular material. A dialog is a popup layout that is displayed to a user above all content in the center of the screen, which can easily catch user eyeballs.

How to make material DataTable using Angular 2?

The Material datatable is created by adding the <table> with the mat-table directive. The [dataSource] property takes a collection of data passed to the data table. Each column is created by adding an ng-container element with matColumnDef identifier.


2 Answers

First of all, handling server requests in your controller is a bad idea. As a rule of thumb, use services to delegate calls to the server, and use the controller for "gluing" up your models to your view.

There are a few issues in your code, it should look something like this:

$scope.DeleteUser = function (id) {
    var userId = $scope.users[id].Id;
    $http.delete('/api/users/' + userId)
          .success(function (data) {
             $scope.error = "error " + data;
          });
}

Even if the call to the server was successful, you never updated your front-end model. What you have read on other topics regarding $scope.refresh(), I suppose that has the purpose of fetching the data again, like so:

$scope.refresh = function(){
    $http.get('/api/users')
          .success(function(data){
               $scope.users = data;
          });
}

So in order the refresh your view, you must update your model.

$scope.DeleteUser = function (id) {
    var userId = $scope.users[id].Id;
    $http.delete('/api/users/' + userId)
          .success(function (data) {
             //either this
             $scope.refresh();
             //or this
             $scope.users.splice(id,1);
          });
}
like image 123
Rus Paul Avatar answered Sep 29 '22 09:09

Rus Paul


Two solutions : once you've performed your deletion, remove the user from the users array by doing a slice :

$scope.DeleteUser = function (index) {
    var UserID = $scope.users[index].Id;
    $http.delete('/api/users/' + UserID).then(function(del) {
        $scope.users.splice(index,1);
    });
}

You can get the index of the user by using $index in your ng-repeat but as your code may be asynchronous this is not recommended.

Or, you can just make another get from your API once your deletion is resolved.

$scope.DeleteUser = function (index) {
    var UserID = $scope.users[index].Id;
    $http.delete('/api/users/' + UserID).then(function(del) {
        $http.get('/api/users').then(function(data){
            $scope.users = data;
        });
    });
}

But... What if the person who's using your application is deleting users faster than your API is able to ?

First solution will fail for sure, and the second will hardly maintain you DOM clean as long as all requests came back in the same order they were sent.
One solution is to prevent any request to the API as long as another is already pending.

In JavaScript as Functions are in fact executable Objects they can have properties. So we'll add a isBusy property to the DeleteUser function to know when it is already processing.

$scope.DeleteUser = function (index) {
    if(!$scope.DeleteUser.isBusy){
        var UserID = $scope.users[id].Id;
        $scope.DeleteUser.isBusy = true;

        $http.delete('/api/users/' + UserID).then(function(del) {
            $scope.users.splice(id,1);
            $scope.DeleteUser.isBusy = false;
        });
    }
}

EDIT:

Update code to use .then() on $http promise object as .success() is now deprecated.

like image 25
Freezystem Avatar answered Sep 29 '22 09:09

Freezystem