KYLIN-579 Unload hive table from kylin

Signed-off-by: wangxianbin1987 <wangxianbin1...@gmail.com>


Project: http://git-wip-us.apache.org/repos/asf/kylin/repo
Commit: http://git-wip-us.apache.org/repos/asf/kylin/commit/6db101ed
Tree: http://git-wip-us.apache.org/repos/asf/kylin/tree/6db101ed
Diff: http://git-wip-us.apache.org/repos/asf/kylin/diff/6db101ed

Branch: refs/heads/1.x-HBase1.1.3
Commit: 6db101edff38f6484f805d01a06f79762da9b16a
Parents: 343ce34
Author: wangxianbin1987 <wangxianbin1...@gmail.com>
Authored: Mon Feb 22 17:33:23 2016 +0800
Committer: shaofengshi <shaofeng...@apache.org>
Committed: Fri Feb 26 16:14:52 2016 +0800

----------------------------------------------------------------------
 .../java/org/apache/kylin/cube/CubeManager.java | 34 +++++++++
 .../apache/kylin/metadata/MetadataManager.java  | 18 +++--
 .../kylin/metadata/project/ProjectManager.java  | 31 ++++++++
 .../metadata/tool/HiveSourceTableLoader.java    |  6 ++
 .../kylin/rest/controller/TableController.java  | 67 ++++++++++++++++--
 .../apache/kylin/rest/service/CubeService.java  | 27 ++++++-
 .../kylin/rest/service/ProjectService.java      | 13 ++++
 .../rest/controller/TableControllerTest.java    |  8 ++-
 webapp/app/js/controllers/sourceMeta.js         | 74 ++++++++++++++++++++
 webapp/app/js/services/tables.js                |  1 +
 .../app/partials/tables/source_table_tree.html  | 20 +++++-
 11 files changed, 283 insertions(+), 16 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/cube/src/main/java/org/apache/kylin/cube/CubeManager.java
----------------------------------------------------------------------
diff --git a/cube/src/main/java/org/apache/kylin/cube/CubeManager.java 
b/cube/src/main/java/org/apache/kylin/cube/CubeManager.java
index d3bbf59..6fb907f 100644
--- a/cube/src/main/java/org/apache/kylin/cube/CubeManager.java
+++ b/cube/src/main/java/org/apache/kylin/cube/CubeManager.java
@@ -52,7 +52,9 @@ import org.apache.kylin.metadata.model.PartitionDesc;
 import org.apache.kylin.metadata.model.SegmentStatusEnum;
 import org.apache.kylin.metadata.model.TableDesc;
 import org.apache.kylin.metadata.model.TblColRef;
+import org.apache.kylin.metadata.project.ProjectInstance;
 import org.apache.kylin.metadata.project.ProjectManager;
+import org.apache.kylin.metadata.project.RealizationEntry;
 import org.apache.kylin.metadata.realization.IRealization;
 import org.apache.kylin.metadata.realization.IRealizationConstants;
 import org.apache.kylin.metadata.realization.IRealizationProvider;
@@ -157,6 +159,38 @@ public class CubeManager implements IRealizationProvider {
         return result;
     }
 
+    public boolean isTableInAnyCube(String tableName) {
+        for(ProjectInstance projectInstance : 
ProjectManager.getInstance(config).listAllProjects()) {
+            if(isTableInCube(tableName, projectInstance.getName())) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    public boolean isTableInCube(String tableName, String projectName) {
+        ProjectManager projectManager = ProjectManager.getInstance(config);
+        CubeDescManager cubeDescManager = CubeDescManager.getInstance(config);
+        ProjectInstance projectInstance = 
projectManager.getProject(projectName);
+        if (projectInstance == null) {
+            throw new IllegalStateException("Cannot find project '" + 
projectName + "' in project manager");
+        }
+
+               for (RealizationEntry projectDataModel : 
projectInstance.getRealizationEntries()) {
+                       if (projectDataModel.getType() == RealizationType.CUBE) 
{
+                               CubeDesc cubeDesc = 
cubeDescManager.getCubeDesc(projectDataModel.getRealization());
+                if (cubeDesc == null) {
+                    throw new IllegalStateException("Cannot find cube '" + 
projectDataModel.getRealization() + "' in cubeDesc manager");
+                }
+
+                               if 
(cubeDesc.getModel().getAllTables().contains(tableName.toUpperCase())) {
+                                       return true;
+                               }
+                       }
+               }
+        return false;
+    }
+
     public DictionaryInfo buildDictionary(CubeSegment cubeSeg, TblColRef col, 
String factColumnsPath) throws IOException {
         CubeDesc cubeDesc = cubeSeg.getCubeDesc();
         if (!cubeDesc.getRowkey().isUseDictionary(col))

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/metadata/src/main/java/org/apache/kylin/metadata/MetadataManager.java
----------------------------------------------------------------------
diff --git 
a/metadata/src/main/java/org/apache/kylin/metadata/MetadataManager.java 
b/metadata/src/main/java/org/apache/kylin/metadata/MetadataManager.java
index 800ea44..71e6649 100644
--- a/metadata/src/main/java/org/apache/kylin/metadata/MetadataManager.java
+++ b/metadata/src/main/java/org/apache/kylin/metadata/MetadataManager.java
@@ -22,11 +22,7 @@ import java.io.ByteArrayInputStream;
 import java.io.ByteArrayOutputStream;
 import java.io.IOException;
 import java.io.InputStream;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
+import java.util.*;
 import java.util.Map.Entry;
 import java.util.concurrent.ConcurrentHashMap;
 
@@ -191,6 +187,12 @@ public class MetadataManager {
         srcTableMap.put(srcTable.getIdentity(), srcTable);
     }
 
+    public void removeSourceTable(String tableIdentity) throws IOException {
+        String path = TableDesc.concatResourcePath(tableIdentity);
+        getStore().deleteResource(path);
+        srcTableMap.remove(tableIdentity);
+    }
+
     private void init(KylinConfig config) throws IOException {
         this.config = config;
         reloadAllSourceTable();
@@ -394,6 +396,12 @@ public class MetadataManager {
         srcTableExdMap.putLocal(tableId, tableExdProperties);
     }
 
+    public void removeTableExd(String tableIdentity) throws IOException {
+        String path = TableDesc.concatExdResourcePath(tableIdentity);
+        getStore().deleteResource(path);
+        srcTableExdMap.remove(tableIdentity);
+    }
+
     public String appendDBName(String table) {
 
         if (table.indexOf(".") > 0)

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/metadata/src/main/java/org/apache/kylin/metadata/project/ProjectManager.java
----------------------------------------------------------------------
diff --git 
a/metadata/src/main/java/org/apache/kylin/metadata/project/ProjectManager.java 
b/metadata/src/main/java/org/apache/kylin/metadata/project/ProjectManager.java
index a05128a..8bdfb51 100644
--- 
a/metadata/src/main/java/org/apache/kylin/metadata/project/ProjectManager.java
+++ 
b/metadata/src/main/java/org/apache/kylin/metadata/project/ProjectManager.java
@@ -255,6 +255,18 @@ public class ProjectManager {
         return projectInstance;
     }
 
+       public void removeTableDescFromProject(String tableIdentities, String 
projectName) throws IOException {
+               MetadataManager metaMgr = getMetadataManager();
+               ProjectInstance projectInstance = getProject(projectName);
+               TableDesc table = metaMgr.getTableDesc(tableIdentities);
+               if (table == null) {
+                       throw new IllegalStateException("Cannot find table '" + 
table + "' in metadata manager");
+               }
+
+               projectInstance.removeTable(table.getIdentity());
+               saveResource(projectInstance);
+       }
+
     private void saveResource(ProjectInstance prj) throws IOException {
         ResourceStore store = getStore();
         store.putResource(prj.getResourcePath(), prj, PROJECT_SERIALIZER);
@@ -271,6 +283,25 @@ public class ProjectManager {
         clearL2Cache();
     }
 
+    public boolean isTableInAnyProject(String tableName) {
+        for(ProjectInstance projectInstance : 
ProjectManager.getInstance(config).listAllProjects()) {
+            if(projectInstance.containsTable(tableName.toUpperCase())) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    public boolean isTableInProject(String projectName, String tableName) {
+        ProjectInstance projectInstance = 
ProjectManager.getInstance(config).getProject(projectName);
+        if(projectInstance != null) {
+            if(projectInstance.containsTable(tableName.toUpperCase())) {
+                return true;
+            }
+        }
+        return false;
+    }
+
     public List<ProjectInstance> findProjects(RealizationType type, String 
realizationName) {
         List<ProjectInstance> result = Lists.newArrayList();
         for (ProjectInstance prj : projectMap.values()) {

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/metadata/src/main/java/org/apache/kylin/metadata/tool/HiveSourceTableLoader.java
----------------------------------------------------------------------
diff --git 
a/metadata/src/main/java/org/apache/kylin/metadata/tool/HiveSourceTableLoader.java
 
b/metadata/src/main/java/org/apache/kylin/metadata/tool/HiveSourceTableLoader.java
index 5e64068..39b4f93 100644
--- 
a/metadata/src/main/java/org/apache/kylin/metadata/tool/HiveSourceTableLoader.java
+++ 
b/metadata/src/main/java/org/apache/kylin/metadata/tool/HiveSourceTableLoader.java
@@ -79,6 +79,12 @@ public class HiveSourceTableLoader {
         return loadedTables;
     }
 
+    public static void unLoadHiveTable(String hiveTable) throws IOException {
+        MetadataManager metaMgr = 
MetadataManager.getInstance(KylinConfig.getInstanceFromEnv());
+        metaMgr.removeSourceTable(hiveTable);
+        metaMgr.removeTableExd(hiveTable);
+    }
+
     private static List<String> extractHiveTables(String database, Set<String> 
tables, KylinConfig config) throws IOException {
 
         List<String> loadedTables = Lists.newArrayList();

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/server/src/main/java/org/apache/kylin/rest/controller/TableController.java
----------------------------------------------------------------------
diff --git 
a/server/src/main/java/org/apache/kylin/rest/controller/TableController.java 
b/server/src/main/java/org/apache/kylin/rest/controller/TableController.java
index f899d99..a4d172f 100644
--- a/server/src/main/java/org/apache/kylin/rest/controller/TableController.java
+++ b/server/src/main/java/org/apache/kylin/rest/controller/TableController.java
@@ -19,13 +19,9 @@
 package org.apache.kylin.rest.controller;
 
 import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
+import java.util.*;
 
+import com.google.common.collect.Sets;
 import org.apache.commons.lang.StringUtils;
 import org.apache.kylin.common.util.HiveClient;
 import org.apache.kylin.metadata.MetadataConstants;
@@ -35,6 +31,7 @@ import org.apache.kylin.rest.exception.InternalErrorException;
 import org.apache.kylin.rest.request.CardinalityRequest;
 import org.apache.kylin.rest.response.TableDescResponse;
 import org.apache.kylin.rest.service.CubeService;
+import org.apache.kylin.rest.service.ProjectService;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -57,6 +54,8 @@ public class TableController extends BasicController {
 
     @Autowired
     private CubeService cubeMgmtService;
+    @Autowired
+    private ProjectService projectService;
 
     /**
      * Get available table list of the input database
@@ -126,10 +125,60 @@ public class TableController extends BasicController {
         cubeMgmtService.syncTableToProject(loaded, project);
         Map<String, String[]> result = new HashMap<String, String[]>();
         result.put("result.loaded", loaded);
-        result.put("result.unloaded", new String[] {});
+        result.put("result.unloaded", new String[]{});
+        return result;
+    }
+
+    /**
+     * table may referenced by several projects, and kylin only keep one copy 
of meta for each table.
+     * that's why we have two if statement here.
+     * @param tables
+     * @param project
+     * @throws IOException
+     */
+    @RequestMapping(value = "{tables}/{project}", method = { 
RequestMethod.DELETE })
+    @ResponseBody
+    public Map<String, String[]> unLoadHiveTables(@PathVariable String tables, 
@PathVariable String project) {
+        Set<String> unLoadSuccess = Sets.newHashSet();
+        Set<String> unLoadFail = Sets.newHashSet();
+        Map<String, String[]> result = new HashMap<String, String[]>();
+        for (String tableName : tables.split(",")) {
+            if (unLoadHiveTable(tableName, project)) {
+                unLoadSuccess.add(tableName);
+            } else {
+                unLoadFail.add(tableName);
+            }
+        }
+        result.put("result.unload.success", (String[]) 
unLoadSuccess.toArray(new String[unLoadSuccess.size()]));
+        result.put("result.unload.fail", (String[]) unLoadFail.toArray(new 
String[unLoadFail.size()]));
         return result;
     }
 
+    private boolean unLoadHiveTable(String tableName, String project) {
+        boolean rtn = false;
+        if(!cubeMgmtService.isTableInCube(tableName, project)) {
+            try {
+                cubeMgmtService.removeTableFromProject(tableName, project);
+                rtn = true;
+            } catch (IOException e) {
+                logger.error(e.getMessage(), e);
+            }
+        }
+        if(!projectService.isTableInAnyProject(tableName) && 
!cubeMgmtService.isTableInAnyCube(tableName)) {
+            try {
+                cubeMgmtService.unLoadHiveTable(tableName);
+                rtn = true;
+            } catch (IOException e) {
+                logger.error(e.getMessage(), e);
+                rtn = false;
+            }
+        }
+
+        return rtn;
+    }
+
+
+
     /**
      * Regenerate table cardinality
      *
@@ -238,4 +287,8 @@ public class TableController extends BasicController {
         this.cubeMgmtService = cubeService;
     }
 
+    public void setProjectService(ProjectService projectService) {
+        this.projectService = projectService;
+    }
+
 }

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/server/src/main/java/org/apache/kylin/rest/service/CubeService.java
----------------------------------------------------------------------
diff --git 
a/server/src/main/java/org/apache/kylin/rest/service/CubeService.java 
b/server/src/main/java/org/apache/kylin/rest/service/CubeService.java
index 601814c..5020dc3 100644
--- a/server/src/main/java/org/apache/kylin/rest/service/CubeService.java
+++ b/server/src/main/java/org/apache/kylin/rest/service/CubeService.java
@@ -193,6 +193,18 @@ public class CubeService extends BasicService {
         return result;
     }
 
+    public boolean isTableInAnyCube(String tableName) {
+        String[] dbTableName = HadoopUtil.parseHiveTableName(tableName);
+        tableName = dbTableName[0] + "." + dbTableName[1];
+        return getCubeManager().isTableInAnyCube(tableName);
+    }
+
+    public boolean isTableInCube(String tableName, String projectName) {
+        String[] dbTableName = HadoopUtil.parseHiveTableName(tableName);
+        tableName = dbTableName[0] + "." + dbTableName[1];
+        return getCubeManager().isTableInCube(tableName, projectName);
+    }
+
     public boolean isCubeInProject(String projectName, CubeInstance target) {
         ProjectManager projectManager = getProjectManager();
         ProjectInstance project = projectManager.getProject(projectName);
@@ -334,7 +346,6 @@ public class CubeService extends BasicService {
      * Update a cube status from disable to ready.
      *
      * @return
-     * @throws CubeIntegrityException
      * @throws IOException
      * @throws JobException
      */
@@ -511,11 +522,25 @@ public class CubeService extends BasicService {
         return (String[]) loaded.toArray(new String[loaded.size()]);
     }
 
+    @PreAuthorize(Constant.ACCESS_HAS_ROLE_MODELER + " or " + 
Constant.ACCESS_HAS_ROLE_ADMIN)
+    public void unLoadHiveTable(String tableName) throws IOException {
+        String[] dbTableName = HadoopUtil.parseHiveTableName(tableName);
+        tableName = dbTableName[0] + "." + dbTableName[1];
+        HiveSourceTableLoader.unLoadHiveTable(tableName.toUpperCase());
+    }
+
     @PreAuthorize(Constant.ACCESS_HAS_ROLE_ADMIN)
     public void syncTableToProject(String[] tables, String project) throws 
IOException {
         getProjectManager().addTableDescToProject(tables, project);
     }
 
+    @PreAuthorize(Constant.ACCESS_HAS_ROLE_ADMIN)
+    public void removeTableFromProject(String tableName, String project) 
throws IOException {
+        String[] dbTableName = HadoopUtil.parseHiveTableName(tableName);
+        tableName = dbTableName[0] + "." + dbTableName[1];
+        getProjectManager().removeTableDescFromProject(tableName, project);
+    }
+
     @PreAuthorize(Constant.ACCESS_HAS_ROLE_MODELER + " or " + 
Constant.ACCESS_HAS_ROLE_ADMIN)
     public void calculateCardinalityIfNotPresent(String[] tables, String 
submitter) throws IOException {
         MetadataManager metaMgr = getMetadataManager();

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/server/src/main/java/org/apache/kylin/rest/service/ProjectService.java
----------------------------------------------------------------------
diff --git 
a/server/src/main/java/org/apache/kylin/rest/service/ProjectService.java 
b/server/src/main/java/org/apache/kylin/rest/service/ProjectService.java
index 4059345..d6a8a07 100644
--- a/server/src/main/java/org/apache/kylin/rest/service/ProjectService.java
+++ b/server/src/main/java/org/apache/kylin/rest/service/ProjectService.java
@@ -22,6 +22,7 @@ import java.io.IOException;
 import java.util.Collections;
 import java.util.List;
 
+import org.apache.kylin.common.util.HadoopUtil;
 import org.apache.kylin.metadata.project.ProjectInstance;
 import org.apache.kylin.metadata.project.ProjectManager;
 import org.apache.kylin.rest.constant.Constant;
@@ -108,6 +109,18 @@ public class ProjectService extends BasicService {
         accessService.clean(project, true);
     }
 
+    public boolean isTableInAnyProject(String tableName) {
+        String[] dbTableName = HadoopUtil.parseHiveTableName(tableName);
+        tableName = dbTableName[0] + "." + dbTableName[1];
+        return getProjectManager().isTableInAnyProject(tableName);
+    }
+
+    public boolean isTableInProject(String projectName, String tableName) {
+        String[] dbTableName = HadoopUtil.parseHiveTableName(tableName);
+        tableName = dbTableName[0] + "." + dbTableName[1];
+        return getProjectManager().isTableInProject(projectName, tableName);
+    }
+
     public void reloadProjectCache(String name) throws IOException {
         getProjectManager().reloadProject(name);
     }

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/server/src/test/java/org/apache/kylin/rest/controller/TableControllerTest.java
----------------------------------------------------------------------
diff --git 
a/server/src/test/java/org/apache/kylin/rest/controller/TableControllerTest.java
 
b/server/src/test/java/org/apache/kylin/rest/controller/TableControllerTest.java
index 4cbd544..4a48285 100644
--- 
a/server/src/test/java/org/apache/kylin/rest/controller/TableControllerTest.java
+++ 
b/server/src/test/java/org/apache/kylin/rest/controller/TableControllerTest.java
@@ -24,6 +24,7 @@ import java.util.Map;
 
 import org.apache.kylin.metadata.model.TableDesc;
 import org.apache.kylin.rest.service.CubeService;
+import org.apache.kylin.rest.service.ProjectService;
 import org.apache.kylin.rest.service.ServiceTestBase;
 import org.junit.Assert;
 import org.junit.Before;
@@ -36,10 +37,11 @@ import 
org.springframework.beans.factory.annotation.Autowired;
 public class TableControllerTest extends ServiceTestBase {
 
     private TableController tableController;
-    private CubeDescController cubeDescController;
 
     @Autowired
     CubeService cubeService;
+    @Autowired
+    ProjectService projectService;
 
     @Before
     public void setup() throws Exception {
@@ -47,6 +49,7 @@ public class TableControllerTest extends ServiceTestBase {
 
         tableController = new TableController();
         tableController.setCubeService(cubeService);
+        tableController.setProjectService(projectService);
     }
 
     @Test
@@ -69,5 +72,8 @@ public class TableControllerTest extends ServiceTestBase {
         Assert.assertNotNull(loadResult);
 
         Assert.assertTrue(loadResult.get("result.loaded").length == 2);
+
+        loadResult = 
tableController.unLoadHiveTables("TEST_CATEGORY_GROUPINGS","default");
+        
Assert.assertTrue(loadResult.get("result.unload.success")[0].equals("TEST_CATEGORY_GROUPINGS"));
     }
 }

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/webapp/app/js/controllers/sourceMeta.js
----------------------------------------------------------------------
diff --git a/webapp/app/js/controllers/sourceMeta.js 
b/webapp/app/js/controllers/sourceMeta.js
index 5c32f87..9c1fad2 100755
--- a/webapp/app/js/controllers/sourceMeta.js
+++ b/webapp/app/js/controllers/sourceMeta.js
@@ -119,6 +119,24 @@ KylinApp
       });
     };
 
+    $scope.openUnLoadModal = function () {
+      $modal.open({
+        templateUrl: 'removeHiveTable.html',
+        controller: ModalInstanceCtrl,
+        resolve: {
+          tableNames: function () {
+            return $scope.tableNames;
+          },
+          projectName: function () {
+            return $scope.projectModel.selectedProject;
+          },
+          scope: function () {
+            return $scope;
+          }
+        }
+      });
+    };
+
     var ModalInstanceCtrl = function ($scope, $location, $modalInstance, 
kylinConfig,tableNames, MessageService, projectName, scope) {
       $scope.tableNames = "";
       $scope.projectName = projectName;
@@ -327,6 +345,62 @@ KylinApp
           loadingRequest.hide();
         })
       }
+
+      $scope.remove = function () {
+
+        if($scope.tableNames.length === 0 && $scope.selectedNodes.length > 0) {
+          for(var i = 0; i <  $scope.selectedNodes.length; i++){
+            if($scope.selectedNodes[i].label.indexOf(".") >= 0){
+              $scope.tableNames += ($scope.selectedNodes[i].label) += ',';
+            }
+          }
+        }
+
+        if ($scope.tableNames.trim() === "") {
+          SweetAlert.swal('', 'Please input table(s) you want to 
synchronize.', 'info');
+          return;
+        }
+
+        if (!$scope.projectName) {
+          SweetAlert.swal('', 'Please choose your project first!.', 'info');
+          return;
+        }
+
+        $scope.cancel();
+        loadingRequest.show();
+        TableService.unLoadHiveTable({tableName: $scope.tableNames, action: 
projectName}, {}, function (result) {
+          var removedTableInfo = "";
+          angular.forEach(result['result.unload.success'], function (table) {
+            removedTableInfo += "\n" + table;
+          })
+          var unRemovedTableInfo = "";
+          angular.forEach(result['result.unload.fail'], function (table) {
+            unRemovedTableInfo += "\n" + table;
+          })
+
+          if (result['result.unload.fail'].length != 0 && 
result['result.unload.success'].length == 0) {
+            SweetAlert.swal('Failed!', 'Failed to synchronize following 
table(s): ' + unRemovedTableInfo, 'error');
+          }
+          if (result['result.unload.success'].length != 0 && 
result['result.unload.fail'].length == 0) {
+            SweetAlert.swal('Success!', 'The following table(s) have been 
successfully synchronized: ' + removedTableInfo, 'success');
+          }
+          if (result['result.unload.success'].length != 0 && 
result['result.unload.fail'].length != 0) {
+            SweetAlert.swal('Partial unloaded!', 'The following table(s) have 
been successfully synchronized: ' + removedTableInfo + "\n\n Failed to 
synchronize following table(s):" + unRemovedTableInfo, 'warning');
+          }
+          loadingRequest.hide();
+          scope.aceSrcTbLoaded(true);
+
+        }, function (e) {
+          if (e.data && e.data.exception) {
+            var message = e.data.exception;
+            var msg = !!(message) ? message : 'Failed to take action.';
+            SweetAlert.swal('Oops...', msg, 'error');
+          } else {
+            SweetAlert.swal('Oops...', "Failed to take action.", 'error');
+          }
+          loadingRequest.hide();
+        })
+      }
     };
     $scope.trimType = function (typeName) {
       if (typeName.match(/VARCHAR/i)) {

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/webapp/app/js/services/tables.js
----------------------------------------------------------------------
diff --git a/webapp/app/js/services/tables.js b/webapp/app/js/services/tables.js
index e98603b..ccc63c8 100755
--- a/webapp/app/js/services/tables.js
+++ b/webapp/app/js/services/tables.js
@@ -23,6 +23,7 @@ KylinApp.factory('TableService', ['$resource', function 
($resource, config) {
     getExd: {method: 'GET', params: {action: 'exd-map'}, isArray: false},
     reload: {method: 'PUT', params: {action: 'reload'}, isArray: false},
     loadHiveTable: {method: 'POST', params: {}, isArray: false},
+    unLoadHiveTable: {method: 'DELETE', params: {}, isArray: false},
     genCardinality: {method: 'PUT', params: {action: 'cardinality'}, isArray: 
false},
     showHiveDatabases: {method: 'GET', params: {action:'hive'}, cache: true, 
isArray: true},
     showHiveTables: {method: 'GET', params: {action:'hive'}, cache: true, 
isArray: true}  });

http://git-wip-us.apache.org/repos/asf/kylin/blob/6db101ed/webapp/app/partials/tables/source_table_tree.html
----------------------------------------------------------------------
diff --git a/webapp/app/partials/tables/source_table_tree.html 
b/webapp/app/partials/tables/source_table_tree.html
index c048685..522fdbb 100755
--- a/webapp/app/partials/tables/source_table_tree.html
+++ b/webapp/app/partials/tables/source_table_tree.html
@@ -26,9 +26,9 @@
         <div class="col-xs-5" style="padding-left: 0px;margin-top: 20px;">
             <div class="pull-right">
                 <a class="btn btn-xs btn-primary" tooltip="Load Hive Table"  
ng-if="userService.hasRole('ROLE_ADMIN')"  ng-click="openModal()"><i class="fa 
fa-download"></i></a>
-                <a class="btn btn-xs btn-info" tooltip="Load Hive Table From 
Tree"  ng-if="userService.hasRole('ROLE_ADMIN')"  ng-click="openTreeModal()"><i 
class="fa fa-download"></i></a>
-
+                <a class="btn btn-xs btn-primary" tooltip="Load Hive Table 
From Tree"  ng-if="userService.hasRole('ROLE_ADMIN')"  
ng-click="openTreeModal()"><i class="fa fa-download"></i></a>
                 <a class="btn btn-xs btn-success" tooltip="Refresh Tables" 
ng-click="aceSrcTbChanged()"><i class="fa fa-refresh"></i></a>
+                <a class="btn btn-xs btn-info" tooltip="UnLoad Hive Table"  
ng-if="userService.hasRole('ROLE_ADMIN')"  ng-click="openUnLoadModal()"><i 
class="fa fa-remove"></i></a>
             </div>
         </div>
 
@@ -63,6 +63,22 @@
   </div>
 </script>
 
+<script type="text/ng-template" id="removeHiveTable.html">
+  <div class="modal-header">
+    <h4>UnLoad Hive Table Metadata</h4>
+  </div>
+  <div class="modal-body">
+    <span><strong>Project: </strong>{{ 
$parent.projectName!=null?$parent.projectName:'NULL'}}</span>
+    <label for="tables"> Table Names:(Seperate with comma)</label>
+            <textarea ng-model="$parent.tableNames" class="form-control" 
id="removeTables"
+                      placeholder="table1,table2  By default,system will 
choose 'Default' as database,you can specify database like this 
'database.table'"></textarea>
+  </div>
+  <div class="modal-footer">
+    <button class="btn btn-primary" ng-click="remove()">Sync</button>
+    <button class="btn btn-primary" ng-click="cancel()">Cancel</button>
+  </div>
+</script>
+
 <script type="text/ng-template" id="addHiveTableFromTree.html">
   <div class="modal-header"><button class="close" type="button" 
data-dismiss="modal" ng-click="cancel()">×</button>
     <h4>Load Hive Table Metadata From Tree</h4>

Reply via email to